{
  "openapi": "3.1.1",
  "info": {
    "title": "Neostore internal API",
    "version": "v1"
  },
  "servers": [
    {
      "url": "https://app.neostore.cloud",
      "description": "Production Server"
    },
    {
      "url": "https://app-qa.neostore.cloud",
      "description": "Staging Server"
    }
  ],
  "paths": {
    "/api/{tenantId}/admin/automations": {
      "get": {
        "tags": [
          "Automations"
        ],
        "summary": "List the tenant automations",
        "description": "Returns every automation, enabled or not, in declaration order. Unpaged. Returns an empty list when the\ntenant has no automation.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Automations returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "One automation.",
                    "$ref": "#/components/schemas/Automation"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "One automation.",
                    "$ref": "#/components/schemas/Automation"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "One automation.",
                    "$ref": "#/components/schemas/Automation"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.automation:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.automation:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Automations"
        ],
        "summary": "Create an automation",
        "description": "The id must be unique within the tenant and cannot be changed afterwards: execution history is reported\nper automation id.\n            \nA new automation is live as soon as it is created — send `isEnabled: false` to stage one without\nletting it fire. The write lands in the tenant\nconfiguration history and emits an `Automation:Created` event.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The automation to create.",
          "content": {
            "application/json": {
              "schema": {
                "description": "One automation.",
                "$ref": "#/components/schemas/Automation"
              }
            },
            "text/json": {
              "schema": {
                "description": "One automation.",
                "$ref": "#/components/schemas/Automation"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "One automation.",
                "$ref": "#/components/schemas/Automation"
              }
            }
          },
          "required": true
        },
        "responses": {
          "201": {
            "description": "Automation created.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "One automation.",
                  "$ref": "#/components/schemas/Automation"
                }
              },
              "application/json": {
                "schema": {
                  "description": "One automation.",
                  "$ref": "#/components/schemas/Automation"
                }
              },
              "text/json": {
                "schema": {
                  "description": "One automation.",
                  "$ref": "#/components/schemas/Automation"
                }
              }
            }
          },
          "400": {
            "description": "Missing body, invalid id, unknown type, invalid trigger or settings (a past `runAt` or `endDate`, a cron firing more often than every 5 minutes, a `referenceField` no pass template declares as datetime, a reference to something the tenant does not have), or a property the model does not declare. The problem names the refused field.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.automation:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "An automation with that id already exists, or another automation write is in progress or completed since the automations were read; retry.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.automation:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/automations/{automationId}": {
      "delete": {
        "tags": [
          "Automations"
        ],
        "summary": "Delete an automation",
        "description": "The automation stops firing immediately and its configuration is gone. Its execution history is not\ndeleted and stays queryable by id.\n            \nPending per-pass runs already scheduled by the automation are deleted with it. To stop an automation\nwhile keeping it, send `isEnabled: false` to the update endpoint instead. Emits an\n`Automation:Deleted` event.",
        "parameters": [
          {
            "name": "automationId",
            "in": "path",
            "description": "Automation id, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Automation deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.automation:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No automation with that id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "Another automation write is in progress or completed since the automations were read; retry.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.automation:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Automations"
        ],
        "summary": "Get one automation",
        "parameters": [
          {
            "name": "automationId",
            "in": "path",
            "description": "Automation id, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Automation returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "One automation.",
                  "$ref": "#/components/schemas/Automation"
                }
              },
              "application/json": {
                "schema": {
                  "description": "One automation.",
                  "$ref": "#/components/schemas/Automation"
                }
              },
              "text/json": {
                "schema": {
                  "description": "One automation.",
                  "$ref": "#/components/schemas/Automation"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.automation:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No automation with that id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.automation:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Automations"
        ],
        "summary": "Replace an automation",
        "description": "A full replace, not a merge: what is not sent is not kept. The id in the route wins over the id in\nthe body — an automation id cannot be changed.\n            \nDisabling an automation is this endpoint with `isEnabled: false`; the emitted\n`Automation:Updated` event then carries a `stateChange`.\n            \nRules that judge a value in time (`runAt` in the future, the 5-minute cron floor, the\n`displayName` length, a benefit template with an end date) apply only to a value that changes, so a\nbody read with `GET` can always be sent back.",
        "parameters": [
          {
            "name": "automationId",
            "in": "path",
            "description": "Automation id, case-sensitive. Wins over the `id` of the body.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The automation as it should now stand.",
          "content": {
            "application/json": {
              "schema": {
                "description": "One automation.",
                "$ref": "#/components/schemas/Automation"
              }
            },
            "text/json": {
              "schema": {
                "description": "One automation.",
                "$ref": "#/components/schemas/Automation"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "One automation.",
                "$ref": "#/components/schemas/Automation"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Automation updated.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "One automation.",
                  "$ref": "#/components/schemas/Automation"
                }
              },
              "application/json": {
                "schema": {
                  "description": "One automation.",
                  "$ref": "#/components/schemas/Automation"
                }
              },
              "text/json": {
                "schema": {
                  "description": "One automation.",
                  "$ref": "#/components/schemas/Automation"
                }
              }
            }
          },
          "400": {
            "description": "Missing body, unknown type, invalid trigger or settings, or a property the model does not declare. The problem names the refused field.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.automation:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No automation with that id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "Another automation write is in progress or completed since the automations were read; retry.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.automation:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/automations/{taskId}/executions": {
      "get": {
        "tags": [
          "Automations"
        ],
        "summary": "Get execution history for an automation",
        "description": "Returns the runs of one automation over the last 90 days: its occurrences, the per-pass runs it\nstarted, and the backfills a reset or a configuration change started for it. A deleted automation\nstill has its history, and an unknown id returns an empty list.\n            \n**Sorting:** By `startDate`, `taskId`, `taskType`, `duration`, or `retryIndex`.\n            \n**Pagination:** Zero-based `pageIndex` and `pageSize`. Total count in `x-pagination-total` header.",
        "parameters": [
          {
            "name": "taskId",
            "in": "path",
            "description": "Id of the automation, case-sensitive. A trailing `*` matches every automation whose id starts with\nthe rest.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "pageIndex",
            "in": "query",
            "description": "Zero-based page index. Defaults to `0`.",
            "schema": {
              "type": "integer",
              "format": "int32",
              "default": 0
            }
          },
          {
            "name": "pageSize",
            "in": "query",
            "description": "Number of executions per page, 1 to 200. Defaults to `20`.",
            "schema": {
              "type": "integer",
              "format": "int32",
              "default": 20
            }
          },
          {
            "name": "sortBy",
            "in": "query",
            "description": "Sort keys, as `sortBy[i].field` and `sortBy[i].direction`. Defaults to startDate DESC.",
            "schema": {
              "type": "array",
              "items": {
                "description": "One sort key of an execution list, passed as `sortBy[i].field` and `sortBy[i].direction`.\nKeys apply in order; ties are then broken by execution id, descending.",
                "$ref": "#/components/schemas/AutomationSortModel"
              }
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Execution history retrieved successfully",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "oneOf": [
                      {
                        "description": "One delivery of an automation run. An occurrence that was postponed appears once per delivery.",
                        "$ref": "#/components/schemas/Execution"
                      },
                      {
                        "$ref": "#/components/schemas/ExecutionSummary"
                      },
                      {
                        "$ref": "#/components/schemas/ExecutionDetail"
                      }
                    ],
                    "description": "One delivery of an automation run. An occurrence that was postponed appears once per delivery."
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "oneOf": [
                      {
                        "$ref": "#/components/schemas/Execution"
                      },
                      {
                        "$ref": "#/components/schemas/ExecutionSummary"
                      },
                      {
                        "$ref": "#/components/schemas/ExecutionDetail"
                      }
                    ],
                    "description": "One delivery of an automation run. An occurrence that was postponed appears once per delivery."
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "oneOf": [
                      {
                        "$ref": "#/components/schemas/Execution"
                      },
                      {
                        "$ref": "#/components/schemas/ExecutionSummary"
                      },
                      {
                        "$ref": "#/components/schemas/ExecutionDetail"
                      }
                    ],
                    "description": "One delivery of an automation run. An occurrence that was postponed appears once per delivery."
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid taskId format or query parameter",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.automation:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.automation:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/automations/{taskId}/executions/{executionId}": {
      "get": {
        "tags": [
          "Automations"
        ],
        "summary": "Retrieve a specific automation execution with its associated logs.",
        "description": "Returns the delivery with every log message and outgoing call recorded for it. Only the last 90 days\nare searched.",
        "parameters": [
          {
            "name": "taskId",
            "in": "path",
            "description": "Id of the automation, case-sensitive; the execution must belong to it.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "executionId",
            "in": "path",
            "description": "The `id` of an execution, as listed by the execution endpoints.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Execution details with logs retrieved successfully",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "An Neo.Web.Api.Scheduler.Controllers.AutomationsController.Execution with the log messages and outgoing calls recorded for it.",
                  "$ref": "#/components/schemas/ExecutionDetail"
                }
              },
              "application/json": {
                "schema": {
                  "description": "An Neo.Web.Api.Scheduler.Controllers.AutomationsController.Execution with the log messages and outgoing calls recorded for it.",
                  "$ref": "#/components/schemas/ExecutionDetail"
                }
              },
              "text/json": {
                "schema": {
                  "description": "An Neo.Web.Api.Scheduler.Controllers.AutomationsController.Execution with the log messages and outgoing calls recorded for it.",
                  "$ref": "#/components/schemas/ExecutionDetail"
                }
              }
            }
          },
          "400": {
            "description": "Invalid taskId or executionId format",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.automation:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No execution with this id for this automation in the last 90 days.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.automation:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/automations/{taskId}/reset": {
      "post": {
        "tags": [
          "Automations"
        ],
        "summary": "Reset an automation",
        "description": "Recomputes which passes the automation still has to act on. What a reset does depends on the\nautomation's trigger type:\n            \n- **dateRelative:** discards the per-pass runs that have not fired yet, then starts a\n  `dateRelative.backfill` that schedules them again from the current pass data. Runs that\n  already fired are kept, so a reset never acts on a pass twice. The response returns as soon as the\n  backfill is started; follow its progress in the automation's executions using the returned\n  correlationId.\n- **fixedDate (continuous audience):** starts a `continuousAudience.backfill` catch-up scan so\n  passes that newly match are picked up straight away. Passes already processed or already scheduled\n  are left untouched.\n- **recurrence, fixedDate (snapshot), event:** refused with a 409.\n            \nSafe to call repeatedly: a repeated reset leads to the same result.",
        "parameters": [
          {
            "name": "taskId",
            "in": "path",
            "description": "Id of the automation, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Reset accepted and dispatched",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "What a reset did. The backfill it starts runs after the response is returned.",
                  "$ref": "#/components/schemas/ResetResult"
                }
              },
              "application/json": {
                "schema": {
                  "description": "What a reset did. The backfill it starts runs after the response is returned.",
                  "$ref": "#/components/schemas/ResetResult"
                }
              },
              "text/json": {
                "schema": {
                  "description": "What a reset did. The backfill it starts runs after the response is returned.",
                  "$ref": "#/components/schemas/ResetResult"
                }
              }
            }
          },
          "400": {
            "description": "taskId is not 1 to 200 letters, digits, `_` or `-`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.automation:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No automation with that id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "Reset is not available for the automation's trigger type",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.automation:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/automations/executions": {
      "get": {
        "tags": [
          "Automations"
        ],
        "summary": "List recent automation executions for the tenant",
        "description": "Returns the most recent automation executions across all configured automations for the tenant.\nUseful to monitor automation health, spot failing automations and drill into individual executions.\n            \nOnly the runs that belong to an automation are listed, so every row can be opened under it; runs not\nstarted by an automation are left out.\n            \n**Sorting:** By `startDate`, `taskId`, `taskType`, `duration`, or `retryIndex`.\n            \n**Pagination:** Zero-based `pageIndex` and `pageSize`. Total count in `x-pagination-total` header.\n            \nOnly the last 90 days are searched.",
        "parameters": [
          {
            "name": "pageIndex",
            "in": "query",
            "description": "Zero-based page index. Defaults to `0`.",
            "schema": {
              "type": "integer",
              "format": "int32",
              "default": 0
            }
          },
          {
            "name": "pageSize",
            "in": "query",
            "description": "Number of executions per page, 1 to 200. Defaults to `20`.",
            "schema": {
              "type": "integer",
              "format": "int32",
              "default": 20
            }
          },
          {
            "name": "sortBy",
            "in": "query",
            "description": "Sort keys, as `sortBy[i].field` and `sortBy[i].direction`. Defaults to startDate DESC.",
            "schema": {
              "type": "array",
              "items": {
                "description": "One sort key of an execution list, passed as `sortBy[i].field` and `sortBy[i].direction`.\nKeys apply in order; ties are then broken by execution id, descending.",
                "$ref": "#/components/schemas/AutomationSortModel"
              }
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Execution list retrieved successfully",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "An Neo.Web.Api.Scheduler.Controllers.AutomationsController.Execution listed across every automation, with the automation it belongs to.",
                    "$ref": "#/components/schemas/ExecutionSummary"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "An Neo.Web.Api.Scheduler.Controllers.AutomationsController.Execution listed across every automation, with the automation it belongs to.",
                    "$ref": "#/components/schemas/ExecutionSummary"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "An Neo.Web.Api.Scheduler.Controllers.AutomationsController.Execution listed across every automation, with the automation it belongs to.",
                    "$ref": "#/components/schemas/ExecutionSummary"
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid query parameter",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.automation:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.automation:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/themes": {
      "get": {
        "tags": [
          "Theme"
        ],
        "summary": "List every theme of the tenant, in declaration order.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Themes returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                    "$ref": "#/components/schemas/PassTheme"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                    "$ref": "#/components/schemas/PassTheme"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                    "$ref": "#/components/schemas/PassTheme"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.theme:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.theme:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Theme"
        ],
        "summary": "Create a theme.",
        "description": "The id must be unique within the tenant and URL-safe: it is the reference passes carry and the prefix\nof the theme's image paths. An image can only be uploaded once the theme exists, so a new theme points\nat `https://` images or none; upload its own images afterwards and reference them with an update.\nSaving adds an entry to the tenant configuration history and emits a theme created event.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Theme payload.",
          "content": {
            "application/json": {
              "schema": {
                "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                "$ref": "#/components/schemas/PassTheme"
              }
            },
            "text/json": {
              "schema": {
                "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                "$ref": "#/components/schemas/PassTheme"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                "$ref": "#/components/schemas/PassTheme"
              }
            }
          },
          "required": true
        },
        "responses": {
          "201": {
            "description": "Theme created.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                  "$ref": "#/components/schemas/PassTheme"
                }
              },
              "application/json": {
                "schema": {
                  "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                  "$ref": "#/components/schemas/PassTheme"
                }
              },
              "text/json": {
                "schema": {
                  "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                  "$ref": "#/components/schemas/PassTheme"
                }
              }
            }
          },
          "400": {
            "description": "Invalid payload or invalid id; `errors` is keyed by the JSON path of each refused value.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.theme:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "A theme with the same id already exists, or another theme write is in progress or landed first: reload and retry.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.theme:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/themes/{themeId}": {
      "delete": {
        "tags": [
          "Theme"
        ],
        "summary": "Delete a theme and all its images.",
        "description": "Refused while any pass still points at the theme or while an enabled automation applies it. The refusal\nlists both, so the caller knows what to move first. A deletion emits a theme deleted event.",
        "parameters": [
          {
            "name": "themeId",
            "in": "path",
            "description": "Theme id, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Theme and its images deleted."
          },
          "400": {
            "description": "Invalid theme id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.theme:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Theme not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The theme is still applied to passes or by an enabled automation (Theme in use problem), or another theme write is in progress or landed first.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Problem returned when a theme still in use is deleted. These members extend the problem details.",
                  "$ref": "#/components/schemas/ThemeInUse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Problem returned when a theme still in use is deleted. These members extend the problem details.",
                  "$ref": "#/components/schemas/ThemeInUse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Problem returned when a theme still in use is deleted. These members extend the problem details.",
                  "$ref": "#/components/schemas/ThemeInUse"
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.theme:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Theme"
        ],
        "summary": "Retrieve a single theme by id.",
        "parameters": [
          {
            "name": "themeId",
            "in": "path",
            "description": "Theme id, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Theme returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                  "$ref": "#/components/schemas/PassTheme"
                }
              },
              "application/json": {
                "schema": {
                  "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                  "$ref": "#/components/schemas/PassTheme"
                }
              },
              "text/json": {
                "schema": {
                  "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                  "$ref": "#/components/schemas/PassTheme"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.theme:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Theme not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.theme:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Theme"
        ],
        "summary": "Update a theme.",
        "description": "Replaces the whole theme: an omitted property is cleared. A theme id is immutable: a body carrying\nanother id than the route is refused. The creation date is preserved and the modification date is\nstamped by the server.\n\nEvery uploaded image of the theme that the saved theme no longer references, in any language, is\ndeleted. Saving adds an entry to the tenant configuration history and emits a theme updated event.",
        "parameters": [
          {
            "name": "themeId",
            "in": "path",
            "description": "Theme id, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Updated theme payload.",
          "content": {
            "application/json": {
              "schema": {
                "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                "$ref": "#/components/schemas/PassTheme"
              }
            },
            "text/json": {
              "schema": {
                "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                "$ref": "#/components/schemas/PassTheme"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                "$ref": "#/components/schemas/PassTheme"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Theme updated.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                  "$ref": "#/components/schemas/PassTheme"
                }
              },
              "application/json": {
                "schema": {
                  "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                  "$ref": "#/components/schemas/PassTheme"
                }
              },
              "text/json": {
                "schema": {
                  "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign.",
                  "$ref": "#/components/schemas/PassTheme"
                }
              }
            }
          },
          "400": {
            "description": "Invalid payload, or a body id other than the route id; `errors` is keyed by the JSON path of each refused value.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.theme:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Theme not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "Another theme write is in progress or landed first: reload and retry.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.theme:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/themes/{themeId}/images": {
      "get": {
        "tags": [
          "Theme"
        ],
        "summary": "List the images uploaded for a theme, referenced or not.",
        "parameters": [
          {
            "name": "themeId",
            "in": "path",
            "description": "Theme id, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Image list returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Reference to an uploaded theme image.",
                    "$ref": "#/components/schemas/ThemeImageInfo"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Reference to an uploaded theme image.",
                    "$ref": "#/components/schemas/ThemeImageInfo"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Reference to an uploaded theme image.",
                    "$ref": "#/components/schemas/ThemeImageInfo"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.theme:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Theme not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.theme:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Theme"
        ],
        "summary": "Upload an image for a theme.",
        "description": "The theme must exist first. A file name starts with a letter or a digit, uses only letters, digits,\n`-` and `_`, and ends in `.png`, `.jpg` or `.jpeg` (`apple-strip.png`);\nuploading the same name again replaces the file. The content must really be a PNG or JPEG matching the\nextension. Metadata is stripped and the image re-compressed, never resized; convert any other format\nbefore uploading it. An uploaded image the theme does not reference is deleted by the next update of\nthe theme.",
        "parameters": [
          {
            "name": "themeId",
            "in": "path",
            "description": "Theme id, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "multipart/form-data": {
              "schema": {
                "type": "object",
                "properties": {
                  "file": {
                    "type": "string",
                    "description": "Image file (multipart/form-data), at most 8 MB.",
                    "format": "binary"
                  }
                }
              },
              "encoding": {
                "file": {
                  "style": "form"
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Image uploaded; returns the path to reference from the theme.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Reference to an uploaded theme image.",
                  "$ref": "#/components/schemas/ThemeImageInfo"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Reference to an uploaded theme image.",
                  "$ref": "#/components/schemas/ThemeImageInfo"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Reference to an uploaded theme image.",
                  "$ref": "#/components/schemas/ThemeImageInfo"
                }
              }
            }
          },
          "400": {
            "description": "Missing or empty file, invalid file name, or content that is not the PNG or JPEG its extension declares.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.theme:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Theme not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "413": {
            "description": "The request body is larger than 8 MB.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.theme:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/themes/{themeId}/images/{fileName}": {
      "delete": {
        "tags": [
          "Theme"
        ],
        "summary": "Delete a theme image.",
        "description": "Deleting an image the theme still references leaves that slot without an image.",
        "parameters": [
          {
            "name": "themeId",
            "in": "path",
            "description": "Theme id, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "fileName",
            "in": "path",
            "description": "Image file name (e.g. `apple-strip.png`).",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Image deleted."
          },
          "400": {
            "description": "Invalid theme id or file name.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.theme:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Image not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.theme:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Theme"
        ],
        "summary": "Retrieve the bytes of a theme image, with the content type of its extension.",
        "parameters": [
          {
            "name": "themeId",
            "in": "path",
            "description": "Theme id, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "fileName",
            "in": "path",
            "description": "Image file name (e.g. `apple-strip.png`).",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Image bytes returned."
          },
          "400": {
            "description": "Invalid theme id or file name.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.theme:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Image not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.theme:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/themes/usage": {
      "get": {
        "tags": [
          "Theme"
        ],
        "summary": "What currently points at each theme: passes, and enabled automations applying it.",
        "description": "One entry per configured theme, in declaration order; an unused theme is reported with `0`\npasses and no automation. A theme with passes or automations cannot be deleted.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Usage returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "What points at one theme.",
                    "$ref": "#/components/schemas/ThemeUsage"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "What points at one theme.",
                    "$ref": "#/components/schemas/ThemeUsage"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "What points at one theme.",
                    "$ref": "#/components/schemas/ThemeUsage"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.theme:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.theme:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/barcode/{type}/{data}": {
      "get": {
        "tags": [
          "Barcode"
        ],
        "summary": "Renders a value as a barcode or QR code PNG.",
        "description": "The value to encode is everything in the path after the barcode type, percent-decoded, so it may contain\n`/` (an encoded URL works).",
        "parameters": [
          {
            "name": "data",
            "in": "path",
            "description": "Value to encode: the rest of the path after the barcode type.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "type",
            "in": "path",
            "description": "Symbology.",
            "required": true,
            "schema": {
              "description": "Barcode symbology to render. In the URL the name is matched case-insensitively.",
              "default": "CODE128",
              "$ref": "#/components/schemas/BarcodeType"
            }
          },
          {
            "name": "fg",
            "in": "query",
            "description": "Query `fg`: colour of the bars, as hex (`RRGGBB` or `RGB`) with or without the leading `#`. Default `000000`.",
            "schema": {
              "type": "string",
              "default": "000000"
            }
          },
          {
            "name": "bg",
            "in": "query",
            "description": "Query `bg`: colour of the background, same format. Default `FFFFFF`.",
            "schema": {
              "type": "string",
              "default": "FFFFFF"
            }
          },
          {
            "name": "w",
            "in": "query",
            "description": "Query `w`: width in pixels, 1 or more, default 300. A QR code is drawn in whole pixels per module, so its image is approximately this wide.",
            "schema": {
              "type": "integer",
              "format": "int32",
              "default": 300
            }
          },
          {
            "name": "h",
            "in": "query",
            "description": "Query `h`: height in pixels, 1 or more, default 50. Applies to linear and PDF417 codes; a QR code is square.",
            "schema": {
              "type": "integer",
              "format": "int32",
              "default": 50
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "PNG image."
          },
          "400": {
            "description": "Unknown barcode type, no value after the type, a value the symbology cannot encode at that size, an unreadable colour, or a width or height below 1.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/benefits": {
      "get": {
        "tags": [
          "Benefits"
        ],
        "summary": "List benefits across all passes with filtering, sorting, and pagination.",
        "description": "Returns a flat, paginated list of benefits enriched with their parent pass data\n(pass type, identifiers, metadata).\n            \n**Benefit filter fields:** `benefitId`, `passId`, `origin.processId`, `type`\n(equals only), and the dates `creationDate`, `lastModificationDate`, `activationDate`,\n`deactivationDate`, `deletionDate` (equals, greater/less than, or equal).\n            \n**Pass filter/sort fields:** `passType`, `passCreationDate`, `passLastUpdateDate`,\n`identifiers.*`, `metadata.*`. A request naming one is refused with a 400 when it matches\ntoo many rows; narrow it with benefit filters.\n            \n**Pagination:** Zero-based `pageIndex` and `pageSize`. Total count in `x-pagination-total` header.\n            \n**Example — benefits for a benefit template:**\n```\nGET /api/{tenantId}/benefits?pageIndex=0&pageSize=20\n    &filter[0].field=origin.processId&filter[0].operator=equals&filter[0].value=benefit-template-id\n    &sortBy[0].field=creationDate&sortBy[0].direction=1\n```",
        "parameters": [
          {
            "name": "pageIndex",
            "in": "query",
            "description": "Zero-based page index.",
            "schema": {
              "type": "integer",
              "format": "int32",
              "default": 0
            }
          },
          {
            "name": "pageSize",
            "in": "query",
            "description": "Number of benefits per page (1-200).",
            "schema": {
              "maximum": 200,
              "minimum": 1,
              "type": "integer",
              "format": "int32",
              "default": 20
            }
          },
          {
            "name": "filter",
            "in": "query",
            "description": "Optional filters applied to benefit or pass fields.",
            "schema": {
              "type": "array",
              "items": {
                "description": "One condition on passes. Several conditions must all hold.",
                "$ref": "#/components/schemas/FilterModel"
              }
            }
          },
          {
            "name": "sortBy",
            "in": "query",
            "description": "Optional sort descriptors. When absent, results are unordered.",
            "schema": {
              "type": "array",
              "items": {
                "description": "One sort key for pass queries. Several keys apply in order, the first one being the primary sort.",
                "$ref": "#/components/schemas/SortModel"
              }
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Paged list of benefits returned successfully.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "One benefit and the pass carrying it, flattened into a single row for the benefits search and its Excel\nexport.",
                    "$ref": "#/components/schemas/BenefitWithPassRow"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "One benefit and the pass carrying it, flattened into a single row for the benefits search and its Excel\nexport.",
                    "$ref": "#/components/schemas/BenefitWithPassRow"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "One benefit and the pass carrying it, flattened into a single row for the benefits search and its Excel\nexport.",
                    "$ref": "#/components/schemas/BenefitWithPassRow"
                  }
                }
              }
            }
          },
          "400": {
            "description": "pageSize is outside 1-200, a filter or sort names an unknown field or an\n             unsupported operator, or a pass-field filter or sort matches too many rows.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/benefits/export/download": {
      "get": {
        "tags": [
          "Benefits"
        ],
        "summary": "Export benefits as an Excel file using a download token.",
        "description": "Returns the xlsx file for a token obtained from `POST export/token`, with the filters and sorts\nsent there. The token is the credential: no Authorization header is needed.",
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "description": "Download token from `POST export/token`.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Excel file returned successfully."
          },
          "400": {
            "description": "Token is missing, or the filters it carries are refused.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "Token is invalid or expired; request a new export link.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/benefits/export/token": {
      "post": {
        "tags": [
          "Benefits"
        ],
        "summary": "Create a time-limited download token for exporting benefits as Excel.",
        "description": "Returns a download URL, valid 30 minutes, that a browser can open directly. The export applies the\nfilters and sorts sent here.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Filters and sort descriptors of the export.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Export token request body.",
                "$ref": "#/components/schemas/ExportTokenRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Export token request body.",
                "$ref": "#/components/schemas/ExportTokenRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Export token request body.",
                "$ref": "#/components/schemas/ExportTokenRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Download token created successfully.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The link the Excel export is downloaded from.",
                  "$ref": "#/components/schemas/BenefitExportTokenResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The link the Excel export is downloaded from.",
                  "$ref": "#/components/schemas/BenefitExportTokenResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The link the Excel export is downloaded from.",
                  "$ref": "#/components/schemas/BenefitExportTokenResponse"
                }
              }
            }
          },
          "400": {
            "description": "A filter or sort names an unknown field or an unsupported operator, or a pass-field filter or sort matches too many rows.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/cache": {
      "delete": {
        "tags": [
          "Cache"
        ],
        "summary": "Clears every entry of the tenant's cache, so the next requests read configuration and data from their source.",
        "description": "Other tenants are not affected. Requests are slower until the cache is warm again.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Cache cleared."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.cache:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.cache:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/customer": {
      "get": {
        "tags": [
          "Customer"
        ],
        "summary": "Returns the account of the holder identified by the customer token.",
        "description": "The account holds the data carried by the customer token, completed with the holder's stored data when\nthe tenant identifies holders. The response always carries an `authenticationToken` the pages can\nreuse.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Account returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "object",
                  "additionalProperties": { },
                  "description": "A holder's account as the enrolment pages exchange it: a flat JSON object whose properties are the\ntenant's enrolment form fields, plus the well-known keys below."
                }
              },
              "application/json": {
                "schema": {
                  "type": "object",
                  "additionalProperties": { },
                  "description": "A holder's account as the enrolment pages exchange it: a flat JSON object whose properties are the\ntenant's enrolment form fields, plus the well-known keys below."
                }
              },
              "text/json": {
                "schema": {
                  "type": "object",
                  "additionalProperties": { },
                  "description": "A holder's account as the enrolment pages exchange it: a flat JSON object whose properties are the\ntenant's enrolment form fields, plus the well-known keys below."
                }
              }
            }
          },
          "401": {
            "description": "No customer token (`Authorization: neo-customer ...`), or a token that identifies no holder.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 300 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "neo-customer": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Customer"
        ],
        "summary": "Submits an enrolment form: validates the holder's data, identifies the holder, and, when a flow is named,\ncreates or updates the holder in the customer directory.",
        "description": "The data is first validated against the tenant's rules. The holder is then identified by caller:\n<list type=\"bullet\"><item>A back-office user or API key with the `tenant.customer:write` scope (in-store enrolment):\nthe account is completed with the holder's stored data. Without `flow`, the call returns 202 with\n`userExists` and the completed account under `challenge.account`. With `flow`, setting\n`neo.createNew` to `true` creates a new holder even when one already matches.</item><item>A holder with a customer token: the token must identify the holder (401 otherwise).</item><item>Any other caller: depending on the tenant's settings, the holder may have to confirm their\nidentity first; the call then returns 202 and a verification message is sent to the holder.</item></list>\nA 202 body is `{ \"userExists\": true|false|null, \"challenge\": ... }`; for an email verification,\n`challenge` is `{ \"email\": ... }`, and a link to continue is mailed to the holder.",
        "parameters": [
          {
            "name": "flow",
            "in": "query",
            "description": "Name of one of the tenant's customer registration flows. Omitted, the data is only validated and\ncompleted, nothing is saved. Set, the flow creates or updates the holder (and typically issues the pass),\nand the response carries `neo.redirect` = `complete`.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The holder's data, as a JSON object of form fields.",
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "additionalProperties": { },
                "description": "A holder's account as the enrolment pages exchange it: a flat JSON object whose properties are the\ntenant's enrolment form fields, plus the well-known keys below."
              }
            },
            "text/json": {
              "schema": {
                "type": "object",
                "additionalProperties": { },
                "description": "A holder's account as the enrolment pages exchange it: a flat JSON object whose properties are the\ntenant's enrolment form fields, plus the well-known keys below."
              }
            },
            "application/*+json": {
              "schema": {
                "type": "object",
                "additionalProperties": { },
                "description": "A holder's account as the enrolment pages exchange it: a flat JSON object whose properties are the\ntenant's enrolment form fields, plus the well-known keys below."
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Account validated, and created or updated when a flow was named.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "object",
                  "additionalProperties": { },
                  "description": "A holder's account as the enrolment pages exchange it: a flat JSON object whose properties are the\ntenant's enrolment form fields, plus the well-known keys below."
                }
              },
              "application/json": {
                "schema": {
                  "type": "object",
                  "additionalProperties": { },
                  "description": "A holder's account as the enrolment pages exchange it: a flat JSON object whose properties are the\ntenant's enrolment form fields, plus the well-known keys below."
                }
              },
              "text/json": {
                "schema": {
                  "type": "object",
                  "additionalProperties": { },
                  "description": "A holder's account as the enrolment pages exchange it: a flat JSON object whose properties are the\ntenant's enrolment form fields, plus the well-known keys below."
                }
              }
            }
          },
          "202": {
            "description": "Verification required, or (for a back-office caller without flow) the lookup result."
          },
          "400": {
            "description": "Account data invalid (`errors` keyed by field, the empty key for the whole account), unknown flow, or account identifiers the tenant does not accept from a caller without a customer token.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "A customer token that identifies no holder.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 300 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/customer/authenticate": {
      "post": {
        "tags": [
          "Customer"
        ],
        "summary": "Exchanges a proof of identity from a sign-in provider for a customer token valid 24 hours.",
        "description": "Send the returned token on the customer endpoints as `Authorization: neo-customer <token>`.",
        "parameters": [
          {
            "name": "provider",
            "in": "query",
            "description": "Sign-in provider: `otp`, `hmac_email`, `apple`, `google`, `facebook`,\n`line`, `actito`, `livestore`, `secutix.movementId`. Only the providers enabled for\nthe tenant are available.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Provider-specific proof, for instance a one-time password or a provider's ID token; its shape is defined by the provider.",
          "content": {
            "application/json": {
              "schema": { }
            },
            "text/json": {
              "schema": { }
            },
            "application/*+json": {
              "schema": { }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Token issued.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "string"
                }
              },
              "application/json": {
                "schema": {
                  "type": "string"
                }
              },
              "text/json": {
                "schema": {
                  "type": "string"
                }
              }
            }
          },
          "400": {
            "description": "No `provider`, a body that is not JSON, or the provider rejected the data (problem `invalid-credentials`).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 50 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/deviceProfiles": {
      "get": {
        "tags": [
          "DeviceProfiles"
        ],
        "summary": "Lists device profiles.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Profiles, each with its warnings.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A reusable scan context a device can run (Breakfast, Gate F, Cloakroom): what it accepts, and when.",
                    "$ref": "#/components/schemas/DeviceProfile"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A reusable scan context a device can run (Breakfast, Gate F, Cloakroom): what it accepts, and when.",
                    "$ref": "#/components/schemas/DeviceProfile"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A reusable scan context a device can run (Breakfast, Gate F, Cloakroom): what it accepts, and when.",
                    "$ref": "#/components/schemas/DeviceProfile"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.device:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "DeviceProfiles"
        ],
        "summary": "Creates a device profile.",
        "description": "`id` is required and must be unique within the tenant. Tags and benefit template ids are trimmed and\ndeduplicated. A benefit template id that does not exist is dropped and reported as a warning rather\nthan refused.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Profile payload.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Payload to create or update a profile.",
                "$ref": "#/components/schemas/UpsertDeviceProfile"
              }
            },
            "text/json": {
              "schema": {
                "description": "Payload to create or update a profile.",
                "$ref": "#/components/schemas/UpsertDeviceProfile"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Payload to create or update a profile.",
                "$ref": "#/components/schemas/UpsertDeviceProfile"
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Profile created; warnings list what was dropped.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A reusable scan context a device can run (Breakfast, Gate F, Cloakroom): what it accepts, and when.",
                  "$ref": "#/components/schemas/DeviceProfile"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A reusable scan context a device can run (Breakfast, Gate F, Cloakroom): what it accepts, and when.",
                  "$ref": "#/components/schemas/DeviceProfile"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A reusable scan context a device can run (Breakfast, Gate F, Cloakroom): what it accepts, and when.",
                  "$ref": "#/components/schemas/DeviceProfile"
                }
              }
            }
          },
          "400": {
            "description": "A field breaks a rule listed on the payload, the settings do not match the type, or `id` is missing or malformed; every broken rule is reported, keyed by its JSON path.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.device:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "A profile with this id already exists.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/deviceProfiles/{profileId}": {
      "delete": {
        "tags": [
          "DeviceProfiles"
        ],
        "summary": "Deletes a device profile.",
        "description": "Refused while any device still lists the profile: remove it from those devices first.",
        "parameters": [
          {
            "name": "profileId",
            "in": "path",
            "description": "Profile identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Profile deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.device:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No profile with this id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "Devices still list the profile (problem `Device profile in use`); `deviceIds` lists them.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "DeviceProfiles"
        ],
        "summary": "Retrieves a device profile.",
        "parameters": [
          {
            "name": "profileId",
            "in": "path",
            "description": "Profile identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The profile, with its warnings.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A reusable scan context a device can run (Breakfast, Gate F, Cloakroom): what it accepts, and when.",
                  "$ref": "#/components/schemas/DeviceProfile"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A reusable scan context a device can run (Breakfast, Gate F, Cloakroom): what it accepts, and when.",
                  "$ref": "#/components/schemas/DeviceProfile"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A reusable scan context a device can run (Breakfast, Gate F, Cloakroom): what it accepts, and when.",
                  "$ref": "#/components/schemas/DeviceProfile"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.device:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No profile with this id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "DeviceProfiles"
        ],
        "summary": "Updates a device profile.",
        "description": "Replaces the whole profile. Benefit template ids that no longer exist are removed, and reported as\nwarnings. The device type cannot change: devices already running the profile are of that type.\n            \nEvery device listing the profile is pushed `settingsChanged`, so it picks up the change without\nreconnecting.",
        "parameters": [
          {
            "name": "profileId",
            "in": "path",
            "description": "Profile identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Profile payload.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Payload to create or update a profile.",
                "$ref": "#/components/schemas/UpsertDeviceProfile"
              }
            },
            "text/json": {
              "schema": {
                "description": "Payload to create or update a profile.",
                "$ref": "#/components/schemas/UpsertDeviceProfile"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Payload to create or update a profile.",
                "$ref": "#/components/schemas/UpsertDeviceProfile"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Profile updated; warnings list what was removed.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A reusable scan context a device can run (Breakfast, Gate F, Cloakroom): what it accepts, and when.",
                  "$ref": "#/components/schemas/DeviceProfile"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A reusable scan context a device can run (Breakfast, Gate F, Cloakroom): what it accepts, and when.",
                  "$ref": "#/components/schemas/DeviceProfile"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A reusable scan context a device can run (Breakfast, Gate F, Cloakroom): what it accepts, and when.",
                  "$ref": "#/components/schemas/DeviceProfile"
                }
              }
            }
          },
          "400": {
            "description": "A field breaks a rule listed on the payload, the settings do not match the type, or the device type changes; every broken rule is reported, keyed by its JSON path.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.device:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No profile with this id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/devices": {
      "get": {
        "tags": [
          "Devices"
        ],
        "summary": "Lists every device of the tenant, with its settings and running session. Not paginated.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Devices returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A registered device as the back office sees it.",
                    "$ref": "#/components/schemas/Device"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A registered device as the back office sees it.",
                    "$ref": "#/components/schemas/Device"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A registered device as the back office sees it.",
                    "$ref": "#/components/schemas/Device"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.device:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Devices"
        ],
        "summary": "Registers a device. It has no API key yet: call `connections/reset` to issue one.",
        "description": "The id is generated. The logo is copied from the tenant's branding at this point. Emits\n`Device:Created`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Device to register.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Payload to create a new device.",
                "$ref": "#/components/schemas/CreateDevice"
              }
            },
            "text/json": {
              "schema": {
                "description": "Payload to create a new device.",
                "$ref": "#/components/schemas/CreateDevice"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Payload to create a new device.",
                "$ref": "#/components/schemas/CreateDevice"
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Device created; `Location` points to it."
          },
          "400": {
            "description": "Missing or too long name, unsupported type, telemetry out of range, or a profile id that is unknown, of another device type or repeated (keyed `profileIds[i]`).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.device:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/devices/{deviceId}": {
      "delete": {
        "tags": [
          "Devices"
        ],
        "summary": "Deletes a device and revokes its API key.",
        "description": "The device can no longer authenticate. A session it was running is closed as `remote`. Emits\n`Device:Deleted` when the device existed. Idempotent: an unknown id also returns 202.",
        "parameters": [
          {
            "name": "deviceId",
            "in": "path",
            "description": "Device identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "202": {
            "description": "Device deleted, or did not exist."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.device:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Devices"
        ],
        "summary": "Retrieves one device, with its settings and running session.",
        "parameters": [
          {
            "name": "deviceId",
            "in": "path",
            "description": "Device identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Device returned."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.device:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No device with this id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Devices"
        ],
        "summary": "Updates a device.",
        "description": "Name, description and enabled status are always replaced; telemetry settings and profiles only when\nsupplied. Disabling the device, or removing the profile its session runs, closes that session as\n`remote`. The device is then pushed `settingsChanged`.",
        "parameters": [
          {
            "name": "deviceId",
            "in": "path",
            "description": "Device identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "New values.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Payload to update a device.",
                "$ref": "#/components/schemas/UpdateDevice"
              }
            },
            "text/json": {
              "schema": {
                "description": "Payload to update a device.",
                "$ref": "#/components/schemas/UpdateDevice"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Payload to update a device.",
                "$ref": "#/components/schemas/UpdateDevice"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Device updated."
          },
          "400": {
            "description": "Missing or too long name, telemetry out of range, or a profile id that is unknown, of another device type or repeated (keyed `profileIds[i]`).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.device:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No device with this id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/devices/{deviceId}/connect": {
      "post": {
        "tags": [
          "Devices"
        ],
        "summary": "Called by a device when it starts: records the connection and returns everything it needs to run.",
        "description": "Returns its settings (with the rotating barcode secret when the tenant has one), the profiles it can run\nin the order it shows them, its current session, and where to listen for pushes. Emits\n`Device:Connected`. To refresh without recording a connection, use `GET settings`. An\nadministrator may also call it for any device.",
        "parameters": [
          {
            "name": "deviceId",
            "in": "path",
            "description": "Device identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Connection recorded.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Everything a device needs to run, returned on connect and on a settings refresh.",
                  "$ref": "#/components/schemas/ConnectResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Everything a device needs to run, returned on connect and on a settings refresh.",
                  "$ref": "#/components/schemas/ConnectResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Everything a device needs to run, returned on connect and on a settings refresh.",
                  "$ref": "#/components/schemas/ConnectResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the `tenant.device:connect` scope, the API key was issued to another device, or the device is disabled (problem `Device disabled`), or the endpoint is not enabled for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No device with this id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:connect"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/devices/{deviceId}/connections/reset": {
      "post": {
        "tags": [
          "Devices"
        ],
        "summary": "Issues a new API key for a device and returns what it needs to connect.",
        "description": "Used to pair a device the first time and to replace a lost or leaked key: the previous key stops working\nimmediately. A disabled key is re-enabled. The key is returned only in this response and cannot be read\nagain.",
        "parameters": [
          {
            "name": "deviceId",
            "in": "path",
            "description": "Device identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Key issued.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "What a device needs to start talking to the platform.",
                  "$ref": "#/components/schemas/ConnectionToken"
                }
              },
              "application/json": {
                "schema": {
                  "description": "What a device needs to start talking to the platform.",
                  "$ref": "#/components/schemas/ConnectionToken"
                }
              },
              "text/json": {
                "schema": {
                  "description": "What a device needs to start talking to the platform.",
                  "$ref": "#/components/schemas/ConnectionToken"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.device:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No device with this id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/devices/{deviceId}/session": {
      "delete": {
        "tags": [
          "DeviceSessions"
        ],
        "summary": "Ends the device's own session.",
        "description": "Called by the device when staff close the session (`manual`, the default) or when the profile's\nwindow ends (`scheduleEnded`). Ending a device that has no session succeeds.\n            \n## Authorization\nRequires the `tenant.device:connect` scope, with the API key issued to `deviceId`. The back office closes a\nsession with `POST session/close` instead.",
        "parameters": [
          {
            "name": "deviceId",
            "in": "path",
            "description": "Device identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "reason",
            "in": "query",
            "description": "Query string: why the device ends it, `manual` when omitted.",
            "schema": {
              "description": "Why a device ended its own session.",
              "$ref": "#/components/schemas/DeviceEndReason"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Session ended, or there was none."
          },
          "400": {
            "description": "Unknown `reason`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller is not the device itself (its own API key, with the `tenant.device:connect` scope), or the endpoint is not enabled for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The device's session changed concurrently; retry.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:connect"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "DeviceSessions"
        ],
        "summary": "Starts a session on a device.",
        "description": "Ends the session the device was running, as `replaced`, and starts one on `profileId`. Starting the\nprofile the device already runs returns that session unchanged, so a retry is safe.\n            \n## Authorization\nRequires the `tenant.device:connect` scope, with the API key issued to `deviceId`: only the device itself starts\na session.",
        "parameters": [
          {
            "name": "deviceId",
            "in": "path",
            "description": "Device identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Profile to run.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Profile a device starts running.",
                "$ref": "#/components/schemas/StartSession"
              }
            },
            "text/json": {
              "schema": {
                "description": "Profile a device starts running.",
                "$ref": "#/components/schemas/StartSession"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Profile a device starts running.",
                "$ref": "#/components/schemas/StartSession"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "The running session.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A device running one profile.",
                  "$ref": "#/components/schemas/DeviceSessionState"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A device running one profile.",
                  "$ref": "#/components/schemas/DeviceSessionState"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A device running one profile.",
                  "$ref": "#/components/schemas/DeviceSessionState"
                }
              }
            }
          },
          "400": {
            "description": "The profile is not one of the device's profiles.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller is not the device itself (its own API key, with the `tenant.device:connect` scope), or the device is disabled (problem `Device disabled`), or the endpoint is not enabled for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No device with this id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The device's session changed concurrently; retry.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:connect"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/devices/{deviceId}/session/close": {
      "post": {
        "tags": [
          "DeviceSessions"
        ],
        "summary": "Closes a device's session remotely.",
        "description": "Ends the session as `remote` and pushes `sessionClosed` to the device. The push is best effort: a\ndevice that missed it finds out on its next request.",
        "parameters": [
          {
            "name": "deviceId",
            "in": "path",
            "description": "Device identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Session closed, or there was none."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.device:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No device with this id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The device's session changed concurrently; retry.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/devices/{deviceId}/settings": {
      "get": {
        "tags": [
          "Devices"
        ],
        "summary": "Refreshes a device's settings without recording a connection.",
        "description": "Returns the same payload as connect. A device calls it on a `settingsChanged` push, or after its\npush connection dropped, to get a fresh push URL and learn whether its session is still running.",
        "parameters": [
          {
            "name": "deviceId",
            "in": "path",
            "description": "Device identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Settings returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Everything a device needs to run, returned on connect and on a settings refresh.",
                  "$ref": "#/components/schemas/ConnectResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Everything a device needs to run, returned on connect and on a settings refresh.",
                  "$ref": "#/components/schemas/ConnectResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Everything a device needs to run, returned on connect and on a settings refresh.",
                  "$ref": "#/components/schemas/ConnectResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the `tenant.device:connect` scope, the API key was issued to another device, or the device is disabled (problem `Device disabled`), or the endpoint is not enabled for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No device with this id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:connect"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/devices/{deviceId}/telemetry": {
      "post": {
        "tags": [
          "DeviceTelemetry"
        ],
        "summary": "Uploads a batch of telemetry recorded on a device.",
        "description": "Accepts logs, errors and product events recorded on the device.\n            \n## Authorization\nRequires the `tenant.device:connect` scope, and the API key must be the one issued to `deviceId`. A device\ncannot submit telemetry for another device.\n            \n## Timestamps\nItem timestamps are corrected by the gap between the batch's `sentAt` and the time the server\nreceives it, so a device clock that is off keeps the spacing between items while the batch lands\nin real time.\n            \n## Idempotency\nRetrying a batch is safe. Submissions are deduplicated on `batchId`; a replay succeeds and reports\nits items as deduplicated rather than recording them again.\n            \n## Sessions and traces\nA batch can hold items recorded under several sessions, so each item carries the `sessionId` it was\nrecorded under and the upload itself is attributed to no session, whatever its `session.id` baggage. An item with a `traceId` and `spanId` is linked to that trace, so it sits in the\nsame operation as the API request it caused.",
        "parameters": [
          {
            "name": "deviceId",
            "in": "path",
            "description": "Device identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The telemetry batch.",
          "content": {
            "application/json": {
              "schema": {
                "description": "A batch of telemetry uploaded by one device in one request.",
                "$ref": "#/components/schemas/DeviceTelemetryBatch"
              }
            },
            "text/json": {
              "schema": {
                "description": "A batch of telemetry uploaded by one device in one request.",
                "$ref": "#/components/schemas/DeviceTelemetryBatch"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "A batch of telemetry uploaded by one device in one request.",
                "$ref": "#/components/schemas/DeviceTelemetryBatch"
              }
            }
          }
        },
        "responses": {
          "202": {
            "description": "Batch processed; the counts say what was kept."
          },
          "400": {
            "description": "Malformed batch, or no `batchId`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the `tenant.device:connect` scope, or the API key was issued to another device, or the endpoint is not enabled for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "413": {
            "description": "The body exceeds 1 MB, or the batch carries more items than the `maxBatchSize` of the device's telemetry settings.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1000 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.device:connect"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/emails/verify": {
      "post": {
        "tags": [
          "EmailVerifier"
        ],
        "summary": "Checks that an email address is well formed and that its domain can receive mail.",
        "description": "The address must be a dot-atom local part, an `@`, and a domain of at least two labels; the domain\nmust publish at least one MX record. A malformed address or a domain without MX is not an error: the\ncall returns 200 with `isValid` set to `false`.",
        "parameters": [
          {
            "name": "email",
            "in": "query",
            "description": "Address to check, sent in the query string.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Check completed; read `isValid`.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Outcome of an email address check.",
                  "$ref": "#/components/schemas/EmailVerificationResult"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Outcome of an email address check.",
                  "$ref": "#/components/schemas/EmailVerificationResult"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Outcome of an email address check.",
                  "$ref": "#/components/schemas/EmailVerificationResult"
                }
              }
            }
          },
          "400": {
            "description": "The `email` query parameter is missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/insights/query": {
      "post": {
        "tags": [
          "Insights"
        ],
        "summary": "Runs a KQL query over the tenant's analytics data and returns the rows.",
        "description": "Parameters are referenced by name in the query, for example\n`{\"query\": \"Events | where Name == eventName | take 100\", \"parameters\": {\"eventName\": \"Pass:Installed\"}}`.\nA query that runs too long returns 504; aggregate or narrow it.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Query text, parameter values and execution settings.",
          "content": {
            "application/json": {
              "schema": {
                "description": "A KQL query to run over the tenant's analytics data.",
                "$ref": "#/components/schemas/QueryRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "A KQL query to run over the tenant's analytics data.",
                "$ref": "#/components/schemas/QueryRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "A KQL query to run over the tenant's analytics data.",
                "$ref": "#/components/schemas/QueryRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Query executed.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Tabular result of a query.",
                  "$ref": "#/components/schemas/QueryResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Tabular result of a query.",
                  "$ref": "#/components/schemas/QueryResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Tabular result of a query.",
                  "$ref": "#/components/schemas/QueryResponse"
                }
              }
            }
          },
          "400": {
            "description": "Empty or invalid query, unknown table or column, invalid or reserved parameter name, `options.maxRows` out of range, or more matching rows than `options.maxRows`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.insights:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 60 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "504": {
            "description": "The query ran too long and was cancelled; aggregate or narrow it."
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.insights:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes": {
      "get": {
        "tags": [
          "Pass"
        ],
        "summary": "Lists passes, filtered, sorted and paged.",
        "description": "**Filtering:** see Neo.Web.Api.Controllers.FilterModel for the fields and operators.\n            \n**Sorting:** see Neo.Web.Api.Controllers.SortModel. Without a sort, the order is unspecified and may change between pages.\n            \n**Pagination:** zero-based `pageIndex` and `pageSize`. The number of passes matching the\nfilters, all pages together, is in the `x-pagination-total` response header.\n            \n**Example — list loyalty passes, page 0:**\n```\nGET /api/{tenantId}/passes?pageIndex=0&pageSize=20\n    &filter[0].field=passType&filter[0].operator=equals&filter[0].value=loyalty\n    &sortBy[0].field=creationDate&sortBy[0].direction=DESC\n```\n**Example — passes installed on Apple Wallet:**\n```\nGET /api/{tenantId}/passes?filter[0].field=installationStatus&filter[0].operator=contains&filter[0].value=apple\n```",
        "parameters": [
          {
            "name": "pageIndex",
            "in": "query",
            "description": "Zero-based page index. Default 0.",
            "schema": {
              "maximum": 2147483647,
              "minimum": 0,
              "type": "integer",
              "format": "int32",
              "default": 0
            }
          },
          {
            "name": "pageSize",
            "in": "query",
            "description": "Passes per page. Default 20; 0 returns an empty page with the total still set.",
            "schema": {
              "maximum": 2147483647,
              "minimum": 0,
              "type": "integer",
              "format": "int32",
              "default": 20
            }
          },
          {
            "name": "filter",
            "in": "query",
            "description": "Query `filter[i].field`, `filter[i].operator`, `filter[i].value`: conditions a pass must all meet.",
            "schema": {
              "type": "array",
              "items": {
                "description": "One condition on passes. Several conditions must all hold.",
                "$ref": "#/components/schemas/FilterModel"
              }
            }
          },
          {
            "name": "sortBy",
            "in": "query",
            "description": "Query `sortBy[i].field`, `sortBy[i].direction`: sort keys, primary first.",
            "schema": {
              "type": "array",
              "items": {
                "description": "One sort key for pass queries. Several keys apply in order, the first one being the primary sort.",
                "$ref": "#/components/schemas/SortModel"
              }
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The page of passes.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A pass as listed by `GET /passes`.",
                    "$ref": "#/components/schemas/Pass"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A pass as listed by `GET /passes`.",
                    "$ref": "#/components/schemas/Pass"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A pass as listed by `GET /passes`.",
                    "$ref": "#/components/schemas/Pass"
                  }
                }
              }
            }
          },
          "400": {
            "description": "A filter or sort names an unsupported field, a filter has no operator, or paging is negative.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "patch": {
        "tags": [
          "Pass"
        ],
        "summary": "Changes a pass, addressed by its pass id or by external identifiers, and pushes the result to the holder's\ndevices.",
        "description": "Same changes and delivery as `PATCH {passId}`.\n            \n**Example — update by platform pass ID:**\n```\nPATCH /api/{tenantId}/passes?id=xK9mP2nQr7sT\n            \n{\n  \"additionalData\": { \"loyaltyTier\": \"gold\" },\n  \"options\": { \"updateMetadata\": true }\n}\n```\n**Example — update by external identifier:**\n```\nPATCH /api/{tenantId}/passes?id.shopify.customerId=12345\n            \n{\n  \"identifiers\": { \"email\": \"user@example.com\" },\n  \"additionalData\": { \"loyaltyTier\": \"gold\" },\n  \"options\": { \"updateMetadata\": false }\n}\n```",
        "parameters": [
          {
            "name": "identifiers",
            "in": "query",
            "description": "Query parameters naming the pass: either `id={passId}` alone, or one or more external identifiers\nprefixed with `id.` (`id.y2.customerId=1233332`). With several external identifiers a pass must\ncarry all of them. The identifiers are meant to name one pass; when several passes match, one of them is\nupdated.",
            "schema": {
              "type": "object",
              "additionalProperties": {
                "type": "string"
              }
            }
          },
          {
            "name": "passType",
            "in": "query",
            "description": "Query: only a pass of this pass template matches. Use `passType` in the body to move the pass to another template.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The changes and how to apply them.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Changes to one pass. Omitted fields are left as they are.",
                "$ref": "#/components/schemas/SingleUpdatePassData"
              }
            },
            "text/json": {
              "schema": {
                "description": "Changes to one pass. Omitted fields are left as they are.",
                "$ref": "#/components/schemas/SingleUpdatePassData"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Changes to one pass. Omitted fields are left as they are.",
                "$ref": "#/components/schemas/SingleUpdatePassData"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Applied and pushed within the request (`options.bypassQueue` true)."
          },
          "202": {
            "description": "Queued."
          },
          "400": {
            "description": "The body's `passType` or `themeId` names a template or theme the tenant does not have, or `id` is combined with other identifiers.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No pass matches the identifiers, or no `id` or `id.` parameter is given.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "Synchronous update only: the pass was changed concurrently; retry the request.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 50000 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Pass"
        ],
        "summary": "Issues a new pass to a holder and returns its id.",
        "description": "**Security:** without the `tenant.pass:write` scope, each identifier must be proven (see\nNeo.Web.Api.Controllers.PassController.PassData.Identifiers); unproven ones are dropped, and the request is refused when none is\nleft. The customer identifiers of an authenticated holder are added.\n            \n**Effects:** the pass is created and a pass-created event is emitted.\nNothing is sent to a device until the holder downloads the pass.\n            \n**Example — create with an HMAC proof:**\n```\nPOST /api/{tenantId}/passes?passType=loyalty\n            \n{\n  \"identifiers\": {\n    \"shopify.customerId\": \"12345\",\n    \"shopify.customerId.hmac\": \"{hmac-of-12345}\"\n  },\n  \"additionalData\": { \"loyaltyTier\": \"silver\" }\n}\n```\n**Example — create with the `tenant.pass:write` scope (no proof required):**\n```\nPOST /api/{tenantId}/passes?passType=loyalty\n            \n{\n  \"identifiers\": { \"shopify.customerId\": \"12345\" },\n  \"additionalData\": { \"loyaltyTier\": \"silver\" }\n}\n```",
        "parameters": [
          {
            "name": "passType",
            "in": "query",
            "description": "Pass template to issue the pass from; matched exactly. Required unless a connector of the tenant picks the template.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Identifiers, data and theme of the pass.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Content of a new pass.",
                "$ref": "#/components/schemas/CreatePassData"
              }
            },
            "text/json": {
              "schema": {
                "description": "Content of a new pass.",
                "$ref": "#/components/schemas/CreatePassData"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Content of a new pass.",
                "$ref": "#/components/schemas/CreatePassData"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "The pass was created; the body is its id.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "string"
                }
              },
              "application/json": {
                "schema": {
                  "type": "string"
                }
              },
              "text/json": {
                "schema": {
                  "type": "string"
                }
              }
            }
          },
          "400": {
            "description": "`passType` or `themeId` names a template or theme the tenant does not have.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated and no identifier could be verified.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller is authenticated without the `tenant.pass:write` scope, and no identifier could be verified, or this action is not enabled for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          },
          { }
        ]
      }
    },
    "/api/{tenantId}/passes/{passId}": {
      "get": {
        "tags": [
          "Pass"
        ],
        "summary": "Downloads a pass for a wallet: the Apple `.pkpass` file, the Google Wallet save token, a preview, or a\nredirect chosen from the device.",
        "description": "Download an Apple Wallet pass:\n```\nGET /api/{tenantId}/passes/xK9mP2nQr7sT?device=apple\n```\nAuto-redirect to the appropriate wallet based on user-agent:\n```\nGET /api/{tenantId}/passes/xK9mP2nQr7sT?device=auto\n```\nTrack the installation source (email campaign, email medium):\n```\nGET /api/{tenantId}/passes/xK9mP2nQr7sT?device=apple&neo.src=email-campaign|email\n```",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass id (5 to 50 letters, digits, `_` or `-`).",
            "required": true,
            "schema": {
              "pattern": "^[\\w-]{5,50}$",
              "type": "string"
            }
          },
          {
            "name": "device",
            "in": "query",
            "description": "`apple`: the signed `.pkpass` file. `google`: the signed JWT that saves the pass to Google\n            Wallet. `preview`: the rendered texts and colors of the Apple pass, as JSON. `auto`: a redirect to\n            `?device=apple` on an iPhone, otherwise to `/view`.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "Tags",
            "in": "query",
            "description": "Comma-separated campaign tags, the first segment of `neo.src`; duplicates are dropped.",
            "schema": {
              "type": "array",
              "items": {
                "type": "string"
              }
            }
          },
          {
            "name": "Medium",
            "in": "query",
            "description": "Channel the link was sent through (for example `email`, `sms`), the second segment.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "Origin",
            "in": "query",
            "description": "Page or system the holder came from, the third segment; defaults to the `Referer` header.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "UserAgent",
            "in": "query",
            "description": "Taken from the request's `User-Agent` header, not from `neo.src`.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The pass content."
          },
          "302": {
            "description": "`device=auto`: redirect to the Apple download or the pass page."
          },
          "400": {
            "description": "`device` is not one of the supported values.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 500 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      },
      "patch": {
        "tags": [
          "Pass"
        ],
        "summary": "Changes a pass, addressed by its pass id, and pushes the result to the holder's devices.",
        "description": "**Changes:** identifiers and `additionalData` are merged into the pass (a blank identifier or a\n`null` data value removes its key; omitted keys are kept). `passType` and `themeId` replace\nthe current ones when sent.\n            \n**Delivery:** queued by default (202). With `options.bypassQueue` the change is stored and pushed\nwithin the request (200).\n            \n**Example — update metadata and push notification:**\n```\nPATCH /api/{tenantId}/passes/xK9mP2nQr7sT\n            \n{\n  \"additionalData\": { \"loyaltyTier\": \"platinum\", \"points\": 5000 },\n  \"options\": { \"updateMetadata\": true, \"bypassQueue\": false }\n}\n```\n**Example — urgent update, bypass queue:**\n```\nPATCH /api/{tenantId}/passes/xK9mP2nQr7sT\n            \n{\n  \"additionalData\": { \"boardingStatus\": \"boarding\" },\n  \"options\": { \"updateMetadata\": true, \"bypassQueue\": true }\n}\n```",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass id (5 to 50 letters, digits, `_` or `-`).",
            "required": true,
            "schema": {
              "pattern": "^[\\w-]{5,50}$",
              "type": "string"
            }
          },
          {
            "name": "passType",
            "in": "query",
            "description": "Query: only a pass of this pass template matches. Use `passType` in the body to move the pass to another template.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The changes and how to apply them.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Changes to one pass. Omitted fields are left as they are.",
                "$ref": "#/components/schemas/SingleUpdatePassData"
              }
            },
            "text/json": {
              "schema": {
                "description": "Changes to one pass. Omitted fields are left as they are.",
                "$ref": "#/components/schemas/SingleUpdatePassData"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Changes to one pass. Omitted fields are left as they are.",
                "$ref": "#/components/schemas/SingleUpdatePassData"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Applied and pushed within the request (`options.bypassQueue` true)."
          },
          "202": {
            "description": "Queued."
          },
          "400": {
            "description": "The body's `passType` or `themeId` names a template or theme the tenant does not have.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No pass has this id, or the pass is not of the pass template given in `passType`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "Synchronous update only: the pass was changed concurrently; retry the request.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 50000 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/{passId}/benefits": {
      "get": {
        "tags": [
          "Benefit"
        ],
        "summary": "List benefits for the specified pass id.",
        "description": "Retrieves all benefits of a pass when its id is already known.\n            \n## Representations\nWith the `tenant.pass:read` scope: every benefit on the pass, every field, unfiltered.\n            \nWithout it, the response is the pass holder's view and holds only:\n- benefits not yet removed — `deletionDate` absent or still in the future;\n- benefits shown on the benefit list page — `showOnBenefitListPage` in the behavior, which an\n  absent behavior includes by default;\n- the holder-facing fields. `origin`, `tags`, `passType`, `behavior.mode`,\n  `data.content`, movement `remarks`, and the removal and modification dates are omitted.\n            \nExpired and exhausted benefits are returned in both cases: they stay on the pass, shown as spent, until\ntheir deletion date.\n            \n## Sorting\nPriority descending. In the holder's view, ties are broken by creation date descending.",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass id.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Benefits returned. An empty array is a normal answer.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Represents a persisted benefit with a required unique identifier.",
                    "$ref": "#/components/schemas/Benefit"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Represents a persisted benefit with a required unique identifier.",
                    "$ref": "#/components/schemas/Benefit"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Represents a persisted benefit with a required unique identifier.",
                    "$ref": "#/components/schemas/Benefit"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The credentials sent are invalid.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Pass not found",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:read"
            ]
          },
          {
            "apiKey": [ ]
          },
          { }
        ]
      },
      "post": {
        "tags": [
          "Benefit"
        ],
        "summary": "Create a benefit for the specified pass id.",
        "description": "Same as M:Neo.Web.Api.Benefit.Controllers.BenefitPassController.AddBenefit(System.Collections.Generic.Dictionary{System.String,System.String},Neo.Web.Api.Benefit.Controllers.BenefitPassController.InsertBenefitRequest,System.Threading.CancellationToken), using the pass id directly instead of resolving it from identifiers.",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass id.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Benefit payload to create.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request model to create a new benefit.",
                "$ref": "#/components/schemas/InsertBenefitRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request model to create a new benefit.",
                "$ref": "#/components/schemas/InsertBenefitRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request model to create a new benefit.",
                "$ref": "#/components/schemas/InsertBenefitRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Benefit created or updated. Returns the benefit ID.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Response payload after a benefit is created or updated via POST.",
                  "$ref": "#/components/schemas/UpsertBenefitResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Response payload after a benefit is created or updated via POST.",
                  "$ref": "#/components/schemas/UpsertBenefitResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Response payload after a benefit is created or updated via POST.",
                  "$ref": "#/components/schemas/UpsertBenefitResponse"
                }
              }
            }
          },
          "400": {
            "description": "The payload is invalid, the category is not allowed for the benefit's type, or `data.movements` is refused.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Pass not found",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The externalId is already bound to a different pass in this tenant, the pass is already carrying the maximum number of benefits, or another request is writing the same benefit.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/{passId}/benefits/{benefitId}": {
      "delete": {
        "tags": [
          "Benefit"
        ],
        "summary": "Delete a benefit for a specific pass.",
        "description": "Removes a benefit from the given pass. Both the pass and the benefit must exist, and the benefit must\nbelong to the pass. Permanent: a deleted benefit cannot be recovered.",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "benefitId",
            "in": "path",
            "description": "Benefit identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Benefit deleted"
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Pass or benefit not found",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Benefit"
        ],
        "summary": "Retrieve a benefit for a specific pass.",
        "description": "Fetches a single benefit belonging to a specific pass.\nEnsures both the pass and benefit exist and are correctly associated.\n\n## Validation\nReturns 404 if either the pass or the benefit is missing,\nor if the benefit does not belong to the specified pass.",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "benefitId",
            "in": "path",
            "description": "Benefit identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Benefit returned",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Represents a persisted benefit with a required unique identifier.",
                  "$ref": "#/components/schemas/Benefit"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Represents a persisted benefit with a required unique identifier.",
                  "$ref": "#/components/schemas/Benefit"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Represents a persisted benefit with a required unique identifier.",
                  "$ref": "#/components/schemas/Benefit"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Pass or benefit not found",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Benefit"
        ],
        "summary": "Create or update a benefit for the specified pass id.",
        "description": "Creates or updates a benefit with the specified `benefitId` for the given pass.\nFields omitted from the payload keep their current value. `data.movements` is accepted only while\nthe benefit has no movement; after that, change its balance with the movements endpoint.",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass id.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "benefitId",
            "in": "path",
            "description": "Unique identifier of the benefit to upsert.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Benefit payload to upsert.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request model to patch an existing benefit.",
                "$ref": "#/components/schemas/PatchBenefitRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request model to patch an existing benefit.",
                "$ref": "#/components/schemas/PatchBenefitRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request model to patch an existing benefit.",
                "$ref": "#/components/schemas/PatchBenefitRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Benefit created or updated."
          },
          "400": {
            "description": "The payload is invalid, the category is not allowed for the benefit's type, or `data.movements` is refused.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Pass not found, or the benefit belongs to another pass",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/{passId}/benefitTemplates/{benefitTemplateId}": {
      "post": {
        "tags": [
          "Benefit"
        ],
        "summary": "Grant a benefit template to a single pass.",
        "description": "The one-customer counterpart of a benefit template campaign, e.g. when support is asked to give this\nholder the voucher.\n            \nIt is not the same thing as creating a benefit by hand: the benefit template's own rules apply. The code\nis generated, the images come from the benefit template, and the activation, end-of-validity and removal\ndates are computed from the benefit template's validity mode.\n            \nRe-granting a benefit template the pass already carries refreshes that benefit from the benefit template's current\ndefinition instead of adding a second one; the movements already applied to it are kept.",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "benefitTemplateId",
            "in": "path",
            "description": "Benefit template identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Benefit template granted, or the benefit it already produced refreshed."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The pass does not exist, or the benefit template is unknown or disabled.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The pass already carries the maximum number of benefits.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/{passId}/connect": {
      "get": {
        "tags": [
          "Pass"
        ],
        "summary": "Returns a WebSocket URL on which a pass page is told when the pass changes, so it can refresh.",
        "description": "```\nGET /api/{tenantId}/passes/xK9mP2nQr7sT/connect\n            \n```",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass id (5 to 50 letters, digits, `_` or `-`).",
            "required": true,
            "schema": {
              "pattern": "^[\\w-]{5,50}$",
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The WebSocket URL.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Where to listen for live changes of one pass.",
                  "$ref": "#/components/schemas/PassConnectResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Where to listen for live changes of one pass.",
                  "$ref": "#/components/schemas/PassConnectResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Where to listen for live changes of one pass.",
                  "$ref": "#/components/schemas/PassConnectResponse"
                }
              }
            }
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No pass has this id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 500 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/passes/{passId}/data": {
      "get": {
        "tags": [
          "Pass"
        ],
        "summary": "Returns the data the pass templates render from for this pass, merged into one object.",
        "description": "Does not change the pass.\n            \n```\nGET /api/{tenantId}/passes/xK9mP2nQr7sT/data\n```",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass id (5 to 50 letters, digits, `_` or `-`).",
            "required": true,
            "schema": {
              "pattern": "^[\\w-]{5,50}$",
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The merged template data."
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/passes/{passId}/data/raw": {
      "get": {
        "tags": [
          "Pass"
        ],
        "summary": "Returns the full pass, extensions and secret included, for diagnostics.",
        "description": "```\nGET /api/{tenantId}/passes/xK9mP2nQr7sT/data/raw\n            \n```",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass id (5 to 50 letters, digits, `_` or `-`).",
            "required": true,
            "schema": {
              "pattern": "^[\\w-]{5,50}$",
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The full pass."
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/passes/{passId}/notification": {
      "put": {
        "tags": [
          "Pass"
        ],
        "summary": "Sends a notification to the holder of a pass, addressed by its pass id.",
        "description": "Delivery is queued by default: a 202 means the notification is accepted, not yet sent; queued delivery\nis at-least-once and unordered. Set `options.bypassQueue` for synchronous delivery, which answers\n200. On Apple the message shows on the pass for the pass template's notification duration and the pass\nis pushed to its devices; on Google it is added as a message on the pass.",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass id assigned by the platform.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The message and delivery options.",
          "content": {
            "application/json": {
              "schema": {
                "description": "The message to show the holder, in one or several languages.",
                "$ref": "#/components/schemas/NotifyRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "The message to show the holder, in one or several languages.",
                "$ref": "#/components/schemas/NotifyRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "The message to show the holder, in one or several languages.",
                "$ref": "#/components/schemas/NotifyRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Notification sent synchronously (`options.bypassQueue` true)."
          },
          "202": {
            "description": "Notification queued for delivery."
          },
          "400": {
            "description": "Neither `content` nor `localizedContent` has text, or `correlationId` is outside 10 to 100 characters.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No pass has this id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 50000 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/{passId}/stamps": {
      "get": {
        "tags": [
          "StampCard"
        ],
        "summary": "Read the stamp board of a pass.",
        "description": "A stamp card that has never been stamped reads as an empty board rather than as missing, so a\ncaller can render a fresh card without special-casing it. A pass of any other kind is a 404,\nwhich is how a client discovers that a pass is not a stamp card.",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Board returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The state of a stamp board.",
                  "$ref": "#/components/schemas/StampCardResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The state of a stamp board.",
                  "$ref": "#/components/schemas/StampCardResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The state of a stamp board.",
                  "$ref": "#/components/schemas/StampCardResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No such pass (type `#not-found`), or the pass is not a stamp card (type `#not-a-stamp-card`).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "StampCard"
        ],
        "summary": "Add stamps to a card, or correct it.",
        "description": "Reaching the goal is handled here: the pass template decides whether the board stays full, clears at\nonce, or clears on the following stamp, and reaching it emits `Pass:GoalReached` so the\nconfigured reward benefit template is granted. Every movement emits `Pass:StampApplied`, a\nclearing emits `Pass:StampsReset`, and the pass is pushed to the holder's devices.\n            \nSend the `count` you last read as `oldValue`: the movement lands only while the board is still\nat that count, so a retry of a request that already succeeded is refused with 409 rather than\nstamping twice. Errors are `application/problem+json`; branch on `type`, not on the message.",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The movement to apply.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request to add stamps to, or correct, a card.",
                "$ref": "#/components/schemas/ApplyStampRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request to add stamps to, or correct, a card.",
                "$ref": "#/components/schemas/ApplyStampRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request to add stamps to, or correct, a card.",
                "$ref": "#/components/schemas/ApplyStampRequest"
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Movement applied; `Location` points to the board.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The outcome of applying a movement.",
                  "$ref": "#/components/schemas/ApplyStampResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The outcome of applying a movement.",
                  "$ref": "#/components/schemas/ApplyStampResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The outcome of applying a movement.",
                  "$ref": "#/components/schemas/ApplyStampResponse"
                }
              }
            }
          },
          "400": {
            "description": "The request is invalid (`value` zero or out of range, `remarks` too long), or the card refuses\nthe movement, by problem type: `#stamp-count-below-zero`, `#stamp-goal-reached` (a full `StayAtGoal` card), or\n`#stamp-target-exceeded` (more than the board has room for, with `roomLeft` in the problem).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No such pass (type `#not-found`), or the pass is not a stamp card (type `#not-a-stamp-card`).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The board is no longer at `oldValue` (type `#stamp-count-changed`, with `currentValue` and `expectedValue`); nothing was applied.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/{passId}/view": {
      "get": {
        "tags": [
          "Pass"
        ],
        "summary": "Redirects to the public page where the holder sees the pass and adds it to a wallet.",
        "description": "The target is `{public site}/{tenantId}/{download page of the pass template}`. The request's query\nparameters are forwarded, with `id` set to the pass id.\n```\nGET /api/{tenantId}/passes/xK9mP2nQr7sT/view\n```",
        "parameters": [
          {
            "name": "passId",
            "in": "path",
            "description": "Pass id.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "302": {
            "description": "Redirect to the download page configured on the pass template."
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No pass has this id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/passes/{passIds}": {
      "get": {
        "tags": [
          "Pass"
        ],
        "summary": "Downloads several passes at once: an Apple `.pkpasses` bundle, or one Google Wallet save token\ncarrying them all.",
        "description": "Download a bundle of Apple Wallet passes:\n```\nGET /api/{tenantId}/passes/xK9mP2nQr7sT,a3Bc4dEf5gHi?device=apple\n```\nRetrieve JSON for Google Wallet:\n```\nGET /api/{tenantId}/passes/xK9mP2nQr7sT,a3Bc4dEf5gHi?device=google\n```",
        "parameters": [
          {
            "name": "passIds",
            "in": "path",
            "description": "At least two comma-separated pass ids, each 5 to 50 letters, digits, `_` or `-`.",
            "required": true,
            "schema": {
              "pattern": "^[\\w-]{5,50},([\\w-]{5,50},?)+$",
              "type": "array",
              "items": {
                "type": "string"
              },
              "description": "Pass ids read from a comma-separated route segment; blank entries are dropped."
            }
          },
          {
            "name": "device",
            "in": "query",
            "description": "`apple` or `google`.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "Tags",
            "in": "query",
            "description": "Comma-separated campaign tags, the first segment of `neo.src`; duplicates are dropped.",
            "schema": {
              "type": "array",
              "items": {
                "type": "string"
              }
            }
          },
          {
            "name": "Medium",
            "in": "query",
            "description": "Channel the link was sent through (for example `email`, `sms`), the second segment.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "Origin",
            "in": "query",
            "description": "Page or system the holder came from, the third segment; defaults to the `Referer` header.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "UserAgent",
            "in": "query",
            "description": "Taken from the request's `User-Agent` header, not from `neo.src`.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The passes."
          },
          "400": {
            "description": "`device` is not `apple` or `google`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/passes/benefits": {
      "get": {
        "tags": [
          "Benefit"
        ],
        "summary": "List benefits for the pass resolved from identifiers.",
        "description": "Benefits are sorted by priority (highest first); movements within each benefit are ordered by date (oldest first).",
        "parameters": [
          {
            "name": "identifiers",
            "in": "query",
            "description": "Pass identifiers (internal or external) used to resolve the pass.",
            "schema": {
              "type": "object",
              "additionalProperties": {
                "type": "string"
              }
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Benefits returned",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Represents a persisted benefit with a required unique identifier.",
                    "$ref": "#/components/schemas/Benefit"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Represents a persisted benefit with a required unique identifier.",
                    "$ref": "#/components/schemas/Benefit"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Represents a persisted benefit with a required unique identifier.",
                    "$ref": "#/components/schemas/Benefit"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Pass not found",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Benefit"
        ],
        "summary": "Create a benefit for the pass identified by the supplied identifiers.",
        "description": "Inserts a new benefit. When `origin.externalId` or `origin.processId` is set, this updates the\nbenefit they identify instead of adding a second one - see their descriptions for the exact key. Use the\nPUT variants to choose the `benefitId` yourself.",
        "parameters": [
          {
            "name": "identifiers",
            "in": "query",
            "description": "Pass identifiers (internal or external) used to resolve the pass.",
            "schema": {
              "type": "object",
              "additionalProperties": {
                "type": "string"
              }
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Benefit payload to create.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request model to create a new benefit.",
                "$ref": "#/components/schemas/InsertBenefitRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request model to create a new benefit.",
                "$ref": "#/components/schemas/InsertBenefitRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request model to create a new benefit.",
                "$ref": "#/components/schemas/InsertBenefitRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Benefit created or updated. Returns the benefit ID.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Response payload after a benefit is created or updated via POST.",
                  "$ref": "#/components/schemas/UpsertBenefitResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Response payload after a benefit is created or updated via POST.",
                  "$ref": "#/components/schemas/UpsertBenefitResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Response payload after a benefit is created or updated via POST.",
                  "$ref": "#/components/schemas/UpsertBenefitResponse"
                }
              }
            }
          },
          "400": {
            "description": "The payload is invalid, the category is not allowed for the benefit's type, or `data.movements` is refused.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Pass not found",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The externalId is already bound to a different pass in this tenant, the pass is already carrying the maximum number of benefits, or another request is writing the same benefit.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/benefits/{benefitId}": {
      "delete": {
        "tags": [
          "Benefit"
        ],
        "summary": "Delete a benefit by its id.",
        "description": "Removes the benefit from the pass that carries it. Permanent: a deleted benefit cannot be\nrecovered.",
        "parameters": [
          {
            "name": "benefitId",
            "in": "path",
            "description": "Benefit identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Benefit deleted"
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Benefit not found",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Benefit"
        ],
        "summary": "Retrieve a benefit by its id.",
        "description": "Looks up a benefit across all passes in the tenant, returning its full content, appearance, and current state.",
        "parameters": [
          {
            "name": "benefitId",
            "in": "path",
            "description": "Benefit identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Benefit returned",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Represents a persisted benefit with a required unique identifier.",
                  "$ref": "#/components/schemas/Benefit"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Represents a persisted benefit with a required unique identifier.",
                  "$ref": "#/components/schemas/Benefit"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Represents a persisted benefit with a required unique identifier.",
                  "$ref": "#/components/schemas/Benefit"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Benefit not found",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Benefit"
        ],
        "summary": "Create or update a benefit for the pass identified by the supplied identifiers.",
        "description": "Creates or updates a benefit with the specified `benefitId` for the resolved pass.\nFields omitted from the payload keep their current value. `data.movements` is accepted only while\nthe benefit has no movement; after that, change its balance with the movements endpoint.",
        "parameters": [
          {
            "name": "identifiers",
            "in": "query",
            "description": "Pass identifiers (internal or external) used to resolve the pass.",
            "schema": {
              "type": "object",
              "additionalProperties": {
                "type": "string"
              }
            }
          },
          {
            "name": "benefitId",
            "in": "path",
            "description": "Unique identifier of the benefit to upsert.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Benefit payload to upsert.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request model to patch an existing benefit.",
                "$ref": "#/components/schemas/PatchBenefitRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request model to patch an existing benefit.",
                "$ref": "#/components/schemas/PatchBenefitRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request model to patch an existing benefit.",
                "$ref": "#/components/schemas/PatchBenefitRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Benefit created or updated."
          },
          "400": {
            "description": "The payload is invalid, the category is not allowed for the benefit's type, or `data.movements` is refused.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Pass not found, or the benefit belongs to another pass",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/benefits/{benefitId}/movements": {
      "post": {
        "tags": [
          "Benefit"
        ],
        "summary": "Apply a movement (transaction) to a benefit's value and return the created movement identifier.",
        "description": "Records a change to a benefit's value (redemption, adjustment, issuance).\nMovements are tracked in the benefit's history for audit purposes and form the basis for computing current value.\n\n## Concurrency Control\nSend in `oldValue` the benefit's value as last read. The movement is applied only while the\nbenefit still has that value, so concurrent updates cannot overwrite each other.\nOtherwise returns 409 Conflict: read the benefit again and retry. If the benefit is missing, returns\n404 Not Found.\n\n## Use Cases\n- Redeeming points or stamps (negative movement)\n- Issuing or adjusting loyalty balance (positive movement)\n- Applying promotional adjustments",
        "parameters": [
          {
            "name": "benefitId",
            "in": "path",
            "description": "Benefit identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Movement request with concurrency check.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request model to apply a movement (transaction) to a benefit's value.",
                "$ref": "#/components/schemas/ApplyMovementRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request model to apply a movement (transaction) to a benefit's value.",
                "$ref": "#/components/schemas/ApplyMovementRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request model to apply a movement (transaction) to a benefit's value.",
                "$ref": "#/components/schemas/ApplyMovementRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Movement applied successfully",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Response payload after a movement is created.",
                  "$ref": "#/components/schemas/MovementResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Response payload after a movement is created.",
                  "$ref": "#/components/schemas/MovementResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Response payload after a movement is created.",
                  "$ref": "#/components/schemas/MovementResponse"
                }
              }
            }
          },
          "400": {
            "description": "Value is zero or not a whole number",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Benefit not found",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "`concurrency-conflict`: the current value does not match `oldValue`; the problem carries\n            `currentValue` and `expectedValue`. `benefit-not-redeemable`: the benefit cannot be used\n            right now. `benefit-ceiling-exceeded`: the movement would take it above what it was issued with; the\n            problem carries `ceiling` and `attemptedValue`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/benefits/origins": {
      "get": {
        "tags": [
          "Benefit"
        ],
        "summary": "List distinct benefit origins with their live benefit count.",
        "description": "Returns one entry per distinct `origin.processId` found across all passes in the tenant,\nalong with a count of the benefits carrying that processId that are not yet past their deletion date.\n            \nCovers both benefit templates and integrations that create benefits with an `origin.processId`.\n            \nMeant for a filter list rather than a live figure: a new origin, or the removal of the last benefit\ncarrying one, can take a short while to show.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Origins returned",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Live benefit count for a given origin process identifier.",
                    "$ref": "#/components/schemas/BenefitOriginSummary"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Live benefit count for a given origin process identifier.",
                    "$ref": "#/components/schemas/BenefitOriginSummary"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Live benefit count for a given origin process identifier.",
                    "$ref": "#/components/schemas/BenefitOriginSummary"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/export/download": {
      "get": {
        "tags": [
          "PassExport"
        ],
        "summary": "Downloads the passes matching the filters sealed in the token, as an Excel file.",
        "description": "The link needs no other credential. The file, named `{tenantId}-passes-{yyyy-MM-dd}.xlsx`, has one row\nper pass with the columns `id`, `secret`, `passType`, `themeId`, `creationDate`\nand `lastUpdateDate` (ISO 8601), `installationStatus` (`apple`, `google`, or both\ncomma-separated), `downloadUrl` (the pass's `/view` link), then one column per\n`identifiers.*`, `metadata.*` and `additionalData.*` key found. Every matching pass is\nexported, without paging.",
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "description": "The `token` query parameter of the link returned by `POST export/token`.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The Excel file."
          },
          "400": {
            "description": "The token is missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The token is invalid, expired, or issued for another tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/passes/export/token": {
      "post": {
        "tags": [
          "PassExport"
        ],
        "summary": "Creates a link that downloads the passes matching the filters as an Excel file.",
        "description": "The link is valid for 30 minutes and needs no Authorization header, so it can be opened directly by a\nbrowser. The filters are checked when the link is created and carried by the link.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Filters, with the same fields and operators as `GET /passes`. Empty or omitted, every pass is exported.",
          "content": {
            "application/json": {
              "schema": {
                "type": "array",
                "items": {
                  "description": "One condition on passes. Several conditions must all hold.",
                  "$ref": "#/components/schemas/FilterModel"
                }
              }
            },
            "text/json": {
              "schema": {
                "type": "array",
                "items": {
                  "description": "One condition on passes. Several conditions must all hold.",
                  "$ref": "#/components/schemas/FilterModel"
                }
              }
            },
            "application/*+json": {
              "schema": {
                "type": "array",
                "items": {
                  "description": "One condition on passes. Several conditions must all hold.",
                  "$ref": "#/components/schemas/FilterModel"
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "The download link.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A link that downloads the export without any other credential.",
                  "$ref": "#/components/schemas/ExportTokenResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A link that downloads the export without any other credential.",
                  "$ref": "#/components/schemas/ExportTokenResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A link that downloads the export without any other credential.",
                  "$ref": "#/components/schemas/ExportTokenResponse"
                }
              }
            }
          },
          "400": {
            "description": "A filter names an unsupported field or has no operator.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/findPass": {
      "get": {
        "tags": [
          "Pass"
        ],
        "summary": "Finds the pass of a holder from their identifiers in another system.",
        "description": "Lookup with an HMAC proof:\n```\nGET /api/{tenantId}/passes/findPass?shopify.customerId=12345&shopify.customerId.hmac={hmac}\n```\nLookup with the `tenant.pass:read` scope (no proof required):\n```\nGET /api/{tenantId}/passes/findPass?shopify.customerId=12345\n```",
        "parameters": [
          {
            "name": "identifiers",
            "in": "query",
            "description": "Every other query parameter, as `{key}={value}`. A pass must carry all of them. Without the\n`tenant.pass:read` scope, each must come with a `{key}.hmac` or `{key}.secret` proof, or be\none the tenant accepts without proof; unproven ones are left out of the search. The customer identifiers of an\nauthenticated holder are added.",
            "schema": {
              "type": "object",
              "additionalProperties": {
                "type": "string"
              }
            }
          },
          {
            "name": "passType",
            "in": "query",
            "description": "Restricts the search to this pass template.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The id of the most recently created matching pass.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "string"
                }
              },
              "application/json": {
                "schema": {
                  "type": "string"
                }
              },
              "text/json": {
                "schema": {
                  "type": "string"
                }
              }
            }
          },
          "204": {
            "description": "No pass matches the identifiers."
          },
          "401": {
            "description": "The caller is not authenticated and no identifier could be verified.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller is authenticated without the `tenant.pass:read` scope, and no identifier could be verified, or this action is not enabled for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/passes/findPasses": {
      "get": {
        "tags": [
          "Pass"
        ],
        "summary": "Lists passes from a list of pass ids, or from a key in a connected system (an order, a subscription) that\nthe connector resolves to passes.",
        "description": "**Direct mode:** `ids=id1,id2` returns one item per id given.\n            \n**Supplier mode:** `ids.{provider}={key}` (for example `ids.shopify=ORDER-12345`) asks that\nconnector for the passes of the key, creating the missing ones. The connector may require\n`ids.{provider}.hmac` or `ids.{provider}.secret` as proof.\n            \n**Preview:** with `includePreview=true`, each item adds `title`, `subTitle`,\n`backgroundColor`, `foregroundColor`, `headerText` and `isEnabled`, rendered from the\nApple pass.\n            \n**Example — direct pass IDs lookup:**\n```\nGET /api/{tenantId}/passes/findPasses?ids=xK9mP2nQr7sT,a3Bc4dEf5gHi\n```\n**Example — resolve via supplier:**\n```\nGET /api/{tenantId}/passes/findPasses?ids.shopify=ORDER-12345&includePreview=true\n```\n**Example — resolve via supplier with HMAC:**\n```\nGET /api/{tenantId}/passes/findPasses?ids.shopify=ORDER-12345&ids.shopify.hmac={hmac}\n```",
        "parameters": [
          {
            "name": "identifiers",
            "in": "query",
            "description": "The query parameters: `ids={csv}`, or a single `ids.{provider}={key}` with its optional proof.\n`ids` takes precedence over `ids.*` parameters.",
            "schema": {
              "type": "object",
              "additionalProperties": {
                "type": "string"
              }
            }
          },
          {
            "name": "includePreview",
            "in": "query",
            "description": "Adds the rendered title, subtitle, colors, header text and enabled state of each pass.",
            "schema": {
              "type": "boolean",
              "default": false
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The passes.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": { }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": { }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": { }
                }
              }
            }
          },
          "400": {
            "description": "Neither `ids` nor an `ids.{provider}` parameter, several providers, an empty provider value, or a provider with no connector.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/passes/notification": {
      "put": {
        "tags": [
          "Pass"
        ],
        "summary": "Sends a notification to the holder of a pass, addressed by its pass id or by external identifiers.",
        "description": "Same delivery as `PUT {passId}/notification`.",
        "parameters": [
          {
            "name": "identifiers",
            "in": "query",
            "description": "Query parameters naming the pass: either `id={passId}` alone, or one or more external identifiers\nprefixed with `id.` (`id.y2.customerId=1233332`). With several external identifiers a pass must\ncarry all of them. The identifiers are meant to name one pass; when several passes match, one of them is\nnotified.",
            "schema": {
              "type": "object",
              "additionalProperties": {
                "type": "string"
              }
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The message and delivery options.",
          "content": {
            "application/json": {
              "schema": {
                "description": "The message to show the holder, in one or several languages.",
                "$ref": "#/components/schemas/NotifyRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "The message to show the holder, in one or several languages.",
                "$ref": "#/components/schemas/NotifyRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "The message to show the holder, in one or several languages.",
                "$ref": "#/components/schemas/NotifyRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Notification sent synchronously (`options.bypassQueue` true)."
          },
          "202": {
            "description": "Notification queued for delivery."
          },
          "400": {
            "description": "Neither `content` nor `localizedContent` has text, `correlationId` is outside 10 to 100 characters, or `id` is combined with other identifiers.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No pass matches the identifiers, or no `id` or `id.` parameter is given.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 50000 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/pushUpdate": {
      "post": {
        "tags": [
          "Pass"
        ],
        "summary": "Applies the same change to every pass matching the filters and pushes each pass to its holder's devices.",
        "description": "**Filtering:** same fields and operators as `GET /passes`. No filter selects every pass of the tenant.\n            \n**Asynchronous:** each pass is queued as its own update, spread over time by `options.throughput`.\nA 200 means scheduled, not done; follow progress with `GET pushUpdate/status` under\n`options.correlationId` (a random id when omitted) and stop it with `POST pushUpdate/{correlationId}/cancel`.\n            \n**Changes:** `additionalData` is merged into each pass and `passType` replaces the template when\nsent. `themeId`: omit to leave each pass on its current theme, send a declared id to apply it, send an\nempty string to remove it. Identifiers are not changed by a bulk update.\n            \n**Example — push a seasonal offer to all loyalty passes:**\n```\nPOST /api/{tenantId}/passes/pushUpdate\n    ?filter[0].field=passType&filter[0].operator=equals&filter[0].value=loyalty\n            \n{\n  \"additionalData\": { \"offer\": \"summer2025\", \"discount\": \"20%\" },\n  \"options\": {\n    \"updateMetadata\": true,\n    \"throughput\": 12,\n    \"correlationId\": \"campaign-summer-2025\"\n  }\n}\n```",
        "parameters": [
          {
            "name": "filter",
            "in": "query",
            "description": "Query `filter[i].field`, `filter[i].operator`, `filter[i].value`: conditions a pass must all meet.",
            "schema": {
              "type": "array",
              "items": {
                "description": "One condition on passes. Several conditions must all hold.",
                "$ref": "#/components/schemas/FilterModel"
              }
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The change applied to each pass, and options. Omitted, each pass is pushed as it is, without recomputing metadata, at the tenant's default throughput.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Changes applied to every pass a bulk update matches. Omitted fields are left as they are on each pass.",
                "$ref": "#/components/schemas/MultipleUpdatePassData"
              }
            },
            "text/json": {
              "schema": {
                "description": "Changes applied to every pass a bulk update matches. Omitted fields are left as they are on each pass.",
                "$ref": "#/components/schemas/MultipleUpdatePassData"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Changes applied to every pass a bulk update matches. Omitted fields are left as they are on each pass.",
                "$ref": "#/components/schemas/MultipleUpdatePassData"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "The passes are scheduled; the body gives how many.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "What a bulk update scheduled.",
                  "$ref": "#/components/schemas/PushUpdateResult"
                }
              },
              "application/json": {
                "schema": {
                  "description": "What a bulk update scheduled.",
                  "$ref": "#/components/schemas/PushUpdateResult"
                }
              },
              "text/json": {
                "schema": {
                  "description": "What a bulk update scheduled.",
                  "$ref": "#/components/schemas/PushUpdateResult"
                }
              }
            }
          },
          "400": {
            "description": "`passType` or `themeId` names a template or theme the tenant does not have, a filter names an unsupported field, or a filter has no operator.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/pushUpdate/{correlationId}/cancel": {
      "post": {
        "tags": [
          "Pass"
        ],
        "summary": "Stops an update operation: its pass updates not yet run are skipped.",
        "description": "Updates already applied stay applied, and one running at that moment may still complete.\n            \n**Example:**\n```\nPOST /api/{tenantId}/passes/pushUpdate/campaign-summer-2025/cancel\n```",
        "parameters": [
          {
            "name": "correlationId",
            "in": "path",
            "description": "The operation's correlation id, as sent in `options.correlationId` or listed as `operationData`.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "The operation is marked cancelled."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/pushUpdate/status": {
      "get": {
        "tags": [
          "Pass"
        ],
        "summary": "Lists the progress of every update operation of the tenant, most recently started first.",
        "description": "An operation is every pass update scheduled under one correlation id: bulk updates, queued single\nupdates (each gets its own random id when none is sent) and synchronous updates sent with a correlation id.\n            \n**Example:**\n```\nGET /api/{tenantId}/passes/pushUpdate/status\n```",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The operations.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Progress of one update operation: every pass update queued or applied under the same correlation id.",
                    "$ref": "#/components/schemas/PushUpdateStatistics"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Progress of one update operation: every pass update queued or applied under the same correlation id.",
                    "$ref": "#/components/schemas/PushUpdateStatistics"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Progress of one update operation: every pass update queued or applied under the same correlation id.",
                    "$ref": "#/components/schemas/PushUpdateStatistics"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/stats": {
      "get": {
        "tags": [
          "Pass"
        ],
        "summary": "Counts issued passes and the passes currently installed on Apple Wallet and Google Wallet.",
        "description": "Counted at the time of the call. For dashboards, trends and breakdowns, use the Insights API.",
        "parameters": [
          {
            "name": "passType",
            "in": "query",
            "description": "Restricts the counts to passes of this pass template. Matched exactly; a name with no pass yields zeros.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The counts.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Pass statistics for the tenant, or for one pass template.",
                  "$ref": "#/components/schemas/PassStatistic"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Pass statistics for the tenant, or for one pass template.",
                  "$ref": "#/components/schemas/PassStatistic"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Pass statistics for the tenant, or for one pass template.",
                  "$ref": "#/components/schemas/PassStatistic"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.pass:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.pass:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/receipts/{token}/pdf": {
      "get": {
        "tags": [
          "Receipt"
        ],
        "summary": "Downloads a purchase receipt as a PDF.",
        "description": "Use the `downloadUrl` of a receipt listed on the holder's account as is; the token cannot be built\nby the caller. The link stays valid for several years and can be opened any number of times.",
        "parameters": [
          {
            "name": "token",
            "in": "path",
            "description": "Token taken from the receipt's download link.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Receipt PDF returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "application/json": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "text/json": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              }
            }
          },
          "400": {
            "description": "The link is invalid or has expired.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/redirect": {
      "get": {
        "tags": [
          "Redirect"
        ],
        "summary": "List every short URL of the tenant.",
        "description": "Unpaged and in no guaranteed order. Short URLs past their expiration date are included.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The tenant's short URLs.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A short URL of the tenant and the page it redirects to.",
                    "$ref": "#/components/schemas/WebRedirectEntity"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A short URL of the tenant and the page it redirects to.",
                    "$ref": "#/components/schemas/WebRedirectEntity"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A short URL of the tenant and the page it redirects to.",
                    "$ref": "#/components/schemas/WebRedirectEntity"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.redirect:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.redirect:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Redirect"
        ],
        "summary": "Create a short URL.",
        "description": "The id is generated by the server; its length comes from `options.length`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Target layout, parameters and options of the short URL.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Short URL to create, or the full replacement of an existing one.",
                "$ref": "#/components/schemas/CreateOrUpdateModel"
              }
            },
            "text/json": {
              "schema": {
                "description": "Short URL to create, or the full replacement of an existing one.",
                "$ref": "#/components/schemas/CreateOrUpdateModel"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Short URL to create, or the full replacement of an existing one.",
                "$ref": "#/components/schemas/CreateOrUpdateModel"
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "The created short URL.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A short URL of the tenant and the page it redirects to.",
                  "$ref": "#/components/schemas/WebRedirectEntity"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A short URL of the tenant and the page it redirects to.",
                  "$ref": "#/components/schemas/WebRedirectEntity"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A short URL of the tenant and the page it redirects to.",
                  "$ref": "#/components/schemas/WebRedirectEntity"
                }
              }
            }
          },
          "400": {
            "description": "`layout` is missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.redirect:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.redirect:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/redirect/{id}": {
      "delete": {
        "tags": [
          "Redirect"
        ],
        "summary": "Delete a short URL.",
        "description": "From then on the shared URL answers 404.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "description": "Short URL id (case-sensitive, at least 3 characters).",
            "required": true,
            "schema": {
              "minLength": 3,
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Deleted, with the short URL as it was.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A short URL of the tenant and the page it redirects to.",
                  "$ref": "#/components/schemas/WebRedirectEntity"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A short URL of the tenant and the page it redirects to.",
                  "$ref": "#/components/schemas/WebRedirectEntity"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A short URL of the tenant and the page it redirects to.",
                  "$ref": "#/components/schemas/WebRedirectEntity"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.redirect:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No short URL with this id in the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.redirect:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Redirect"
        ],
        "summary": "Get one short URL.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "description": "Short URL id (case-sensitive, at least 3 characters).",
            "required": true,
            "schema": {
              "minLength": 3,
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The short URL.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A short URL of the tenant and the page it redirects to.",
                  "$ref": "#/components/schemas/WebRedirectEntity"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A short URL of the tenant and the page it redirects to.",
                  "$ref": "#/components/schemas/WebRedirectEntity"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A short URL of the tenant and the page it redirects to.",
                  "$ref": "#/components/schemas/WebRedirectEntity"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.redirect:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No short URL with this id in the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.redirect:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Redirect"
        ],
        "summary": "Replace the target of a short URL.",
        "description": "The id, the shared URL and the creation date are kept; layout, parameters, label and expiration date\nare replaced by the body, so an omitted one is cleared. `options.length` applies on create only.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "description": "Short URL id (case-sensitive, at least 3 characters).",
            "required": true,
            "schema": {
              "minLength": 3,
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "New layout, parameters and options of the short URL.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Short URL to create, or the full replacement of an existing one.",
                "$ref": "#/components/schemas/CreateOrUpdateModel"
              }
            },
            "text/json": {
              "schema": {
                "description": "Short URL to create, or the full replacement of an existing one.",
                "$ref": "#/components/schemas/CreateOrUpdateModel"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Short URL to create, or the full replacement of an existing one.",
                "$ref": "#/components/schemas/CreateOrUpdateModel"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "The updated short URL.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A short URL of the tenant and the page it redirects to.",
                  "$ref": "#/components/schemas/WebRedirectEntity"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A short URL of the tenant and the page it redirects to.",
                  "$ref": "#/components/schemas/WebRedirectEntity"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A short URL of the tenant and the page it redirects to.",
                  "$ref": "#/components/schemas/WebRedirectEntity"
                }
              }
            }
          },
          "400": {
            "description": "`layout` is missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.redirect:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No short URL with this id in the tenant; nothing was changed.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.redirect:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/scans": {
      "post": {
        "tags": [
          "Scan"
        ],
        "summary": "Records a scan of a pass barcode and returns the pass it belongs to.",
        "description": "The pass is found by exact match of `data` against the barcode values each pass carries; when\nseveral passes carry the value, the most recently updated one wins. A pass-scanned event is emitted for\nthat pass with the scanned data and type, for automations and connected partners. The pass itself is\nnot changed.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The scanned value and how it was captured.",
          "content": {
            "application/json": {
              "schema": {
                "description": "A value read from a pass by a scanner, a camera or a keyboard.",
                "$ref": "#/components/schemas/AddScanRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "A value read from a pass by a scanner, a camera or a keyboard.",
                "$ref": "#/components/schemas/AddScanRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "A value read from a pass by a scanner, a camera or a keyboard.",
                "$ref": "#/components/schemas/AddScanRequest"
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Scan recorded; the body names the pass.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The pass the scanned value resolved to.",
                  "$ref": "#/components/schemas/AddScanResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The pass the scanned value resolved to.",
                  "$ref": "#/components/schemas/AddScanResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The pass the scanned value resolved to.",
                  "$ref": "#/components/schemas/AddScanResponse"
                }
              }
            }
          },
          "400": {
            "description": "`data` is missing or outside 3 to 2048 characters, or `type` is missing or unknown.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.scan:scan</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No pass carries the scanned value.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.scan:scan"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/secrets": {
      "get": {
        "tags": [
          "Secret"
        ],
        "summary": "List the keys of the tenant's secrets, never their values.",
        "description": "Includes a secret outside its validity window, which `GET /{key}` answers with 404.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The tenant's secret keys.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "type": "string"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "type": "string"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "type": "string"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.secret:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.secret:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/secrets/{key}": {
      "delete": {
        "tags": [
          "Secret"
        ],
        "summary": "Delete a secret and every value it holds.",
        "description": "The response is sent once the deletion is complete.",
        "parameters": [
          {
            "name": "key",
            "in": "path",
            "description": "Secret key: 2 to 32 characters, letters, digits and `-` only, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Secret deleted."
          },
          "400": {
            "description": "The key breaks the key format.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.secret:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No secret with this key.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.secret:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Secret"
        ],
        "summary": "Read the value of a secret.",
        "description": "Returns the most recently written value that is currently within its validity window\n(`notBefore` passed, `expiresOn` not reached): an older value stays readable until a newer one\nbecomes valid.",
        "parameters": [
          {
            "name": "key",
            "in": "path",
            "description": "Secret key, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The secret value.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "string"
                }
              },
              "application/json": {
                "schema": {
                  "type": "string"
                }
              },
              "text/json": {
                "schema": {
                  "type": "string"
                }
              }
            }
          },
          "400": {
            "description": "The key breaks the key format.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.secret:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No secret with this key, or none of its values is within its validity window.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.secret:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Secret"
        ],
        "summary": "Write a new value for a secret, creating the key if needed.",
        "description": "Previous values are kept as older versions, not overwritten: a read returns the newest value within its\nvalidity window. Writing a value with a future `notBefore` therefore rotates a secret in place, the\nprevious value being served until then.",
        "parameters": [
          {
            "name": "key",
            "in": "path",
            "description": "Secret key: 2 to 32 characters, letters, digits and `-` only, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The value and its validity window.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Value of a secret and the window during which it can be read.",
                "$ref": "#/components/schemas/SetRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Value of a secret and the window during which it can be read.",
                "$ref": "#/components/schemas/SetRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Value of a secret and the window during which it can be read.",
                "$ref": "#/components/schemas/SetRequest"
              }
            }
          }
        },
        "responses": {
          "204": {
            "description": "Value stored."
          },
          "400": {
            "description": "The key breaks the key format, `value` is missing or blank, or `notBefore` is not earlier than `expiresOn`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.secret:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.secret:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/stores": {
      "get": {
        "tags": [
          "Store"
        ],
        "summary": "Lists the stores the caller may read.",
        "description": "A global or tenant administrator gets every store of the tenant. Any other caller gets the stores its\ntenant permissions grant `tenant.store:read` on, and an empty list when it has none.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Stores returned; possibly empty.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A physical store of the tenant, as supplied by the store provider configured for the tenant.",
                    "$ref": "#/components/schemas/Store"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A physical store of the tenant, as supplied by the store provider configured for the tenant.",
                    "$ref": "#/components/schemas/Store"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A physical store of the tenant, as supplied by the store provider configured for the tenant.",
                    "$ref": "#/components/schemas/Store"
                  }
                }
              }
            }
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant does not exist.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/stores/{storeId}": {
      "get": {
        "tags": [
          "Store"
        ],
        "summary": "Gets one store with its store-specific texts and provider attributes.",
        "parameters": [
          {
            "name": "storeId",
            "in": "path",
            "description": "Identifier of the store.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Store returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A physical store of the tenant, as supplied by the store provider configured for the tenant.",
                  "$ref": "#/components/schemas/Store"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A physical store of the tenant, as supplied by the store provider configured for the tenant.",
                  "$ref": "#/components/schemas/Store"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A physical store of the tenant, as supplied by the store provider configured for the tenant.",
                  "$ref": "#/components/schemas/Store"
                }
              }
            }
          },
          "204": {
            "description": "No store with this identifier; no body."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.store:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant does not exist.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.store:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/stores/{storeId}/additionalResources": {
      "get": {
        "tags": [
          "Store"
        ],
        "summary": "Gets the store-specific texts of a store, keyed by culture name.",
        "description": "Returns, per culture, the texts the tenant defines for the store, for instance\n`{\"en\": {\"hours\": \"Mon-Fri 9AM-9PM\"}}`. A culture with no text for the store is left out, and a\nstore with no text at all, or an unknown storeId, returns an empty object.",
        "parameters": [
          {
            "name": "storeId",
            "in": "path",
            "description": "Identifier of the store.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Texts returned; possibly empty.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "object",
                  "additionalProperties": { }
                }
              },
              "application/json": {
                "schema": {
                  "type": "object",
                  "additionalProperties": { }
                }
              },
              "text/json": {
                "schema": {
                  "type": "object",
                  "additionalProperties": { }
                }
              }
            }
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant does not exist.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/stores/{storeId}/advisors": {
      "get": {
        "tags": [
          "Store"
        ],
        "summary": "Lists the advisors (staff members) of a store.",
        "parameters": [
          {
            "name": "storeId",
            "in": "path",
            "description": "Identifier of the store.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Advisors returned; possibly empty.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A staff member of a store, as supplied by the advisor provider configured for the tenant.",
                    "$ref": "#/components/schemas/Advisor"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A staff member of a store, as supplied by the advisor provider configured for the tenant.",
                    "$ref": "#/components/schemas/Advisor"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A staff member of a store, as supplied by the advisor provider configured for the tenant.",
                    "$ref": "#/components/schemas/Advisor"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.store:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant does not exist.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.store:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/templates/render": {
      "post": {
        "tags": [
          "Templates"
        ],
        "summary": "Render Liquid templates against one shared context.",
        "description": "Uses the tenant's Liquid tags and filters. A failing template does not fail the request: it is reported\nin `errors` at its index and the others still render. Nothing is stored.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The templates, the context they share and the culture.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body for rendering Liquid templates.",
                "$ref": "#/components/schemas/RenderTemplateRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body for rendering Liquid templates.",
                "$ref": "#/components/schemas/RenderTemplateRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body for rendering Liquid templates.",
                "$ref": "#/components/schemas/RenderTemplateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Templates processed; check `errors` for per-template Liquid failures.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Response body returned by M:Neo.Web.Api.Template.Controllers.TemplatesController.Render(Neo.Web.Api.Template.Controllers.TemplatesController.RenderTemplateRequest,System.Threading.CancellationToken).",
                  "$ref": "#/components/schemas/RenderTemplateResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Response body returned by M:Neo.Web.Api.Template.Controllers.TemplatesController.Render(Neo.Web.Api.Template.Controllers.TemplatesController.RenderTemplateRequest,System.Threading.CancellationToken).",
                  "$ref": "#/components/schemas/RenderTemplateResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Response body returned by M:Neo.Web.Api.Template.Controllers.TemplatesController.Render(Neo.Web.Api.Template.Controllers.TemplatesController.RenderTemplateRequest,System.Threading.CancellationToken).",
                  "$ref": "#/components/schemas/RenderTemplateResponse"
                }
              }
            }
          },
          "400": {
            "description": "`templates` is missing, or `culture` is not a known culture.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.core:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.core:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/tokens/generate": {
      "post": {
        "tags": [
          "Security"
        ],
        "summary": "Signs customer tokens carrying the given claims, one token per claim set.",
        "description": "The tokens are accepted wherever a token from `customer/authenticate` is, and act as that holder\nuntil they expire. Example body: `[[{\"type\": \"email\", \"value\": \"jane@example.com\"}]]`.",
        "parameters": [
          {
            "name": "validityDuration",
            "in": "query",
            "description": "Query `validityDuration`: how long the tokens stay valid, as a positive duration\n(`d.hh:mm:ss`, for instance `30.00:00:00`). Omitted, the tokens are valid 10 years.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Claim sets; the response has one token per set, in the same order.",
          "content": {
            "application/json": {
              "schema": {
                "type": "array",
                "items": {
                  "type": "array",
                  "items": {
                    "description": "One claim to put in a generated token.",
                    "$ref": "#/components/schemas/WebClaim"
                  }
                }
              }
            },
            "text/json": {
              "schema": {
                "type": "array",
                "items": {
                  "type": "array",
                  "items": {
                    "description": "One claim to put in a generated token.",
                    "$ref": "#/components/schemas/WebClaim"
                  }
                }
              }
            },
            "application/*+json": {
              "schema": {
                "type": "array",
                "items": {
                  "type": "array",
                  "items": {
                    "description": "One claim to put in a generated token.",
                    "$ref": "#/components/schemas/WebClaim"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Tokens issued.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "type": "string"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "type": "string"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "type": "string"
                  }
                }
              }
            }
          },
          "400": {
            "description": "`validityDuration` is not a positive duration.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.authenticationToken:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.authenticationToken:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/webhooks": {
      "get": {
        "tags": [
          "WebHook"
        ],
        "summary": "Lists every webhook subscription of the tenant, enabled or not, with its signature secret.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Subscriptions returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A webhook subscription as stored, with the values the platform generated for it.",
                    "$ref": "#/components/schemas/WebHookWithId"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A webhook subscription as stored, with the values the platform generated for it.",
                    "$ref": "#/components/schemas/WebHookWithId"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A webhook subscription as stored, with the values the platform generated for it.",
                    "$ref": "#/components/schemas/WebHookWithId"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.webhook:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant does not exist.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.webhook:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "WebHook"
        ],
        "summary": "Creates a webhook subscription. The platform generates its identifier and signature secret.",
        "description": "The subscription applies from the next matching event. The response carries the generated `id`\nand `signatureSecret`; the `Location` header points to the subscription.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Events to listen to, the endpoint to call and whether delivery is enabled.",
          "content": {
            "application/json": {
              "schema": {
                "oneOf": [
                  {
                    "$ref": "#/components/schemas/WebHook"
                  },
                  {
                    "$ref": "#/components/schemas/WebHookWithId"
                  }
                ],
                "description": "The caller-editable part of a webhook subscription."
              }
            },
            "text/json": {
              "schema": {
                "oneOf": [
                  {
                    "$ref": "#/components/schemas/WebHook"
                  },
                  {
                    "$ref": "#/components/schemas/WebHookWithId"
                  }
                ],
                "description": "The caller-editable part of a webhook subscription."
              }
            },
            "application/*+json": {
              "schema": {
                "oneOf": [
                  {
                    "$ref": "#/components/schemas/WebHook"
                  },
                  {
                    "$ref": "#/components/schemas/WebHookWithId"
                  }
                ],
                "description": "The caller-editable part of a webhook subscription."
              }
            }
          },
          "required": true
        },
        "responses": {
          "201": {
            "description": "Subscription created.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A webhook subscription as stored, with the values the platform generated for it.",
                  "$ref": "#/components/schemas/WebHookWithId"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A webhook subscription as stored, with the values the platform generated for it.",
                  "$ref": "#/components/schemas/WebHookWithId"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A webhook subscription as stored, with the values the platform generated for it.",
                  "$ref": "#/components/schemas/WebHookWithId"
                }
              }
            }
          },
          "400": {
            "description": "Body missing, `events` empty or missing, or `endpoint` missing or not an absolute `http` or `https` URL.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.webhook:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant does not exist.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.webhook:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/webhooks/{id}": {
      "delete": {
        "tags": [
          "WebHook"
        ],
        "summary": "Deletes a webhook subscription; its endpoint receives no further event.",
        "description": "A recreated subscription gets a new identifier and a new signature secret. The response has no body.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "description": "Identifier the platform assigned to the subscription.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Subscription deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.webhook:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No subscription with this identifier, or the tenant does not exist.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.webhook:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "WebHook"
        ],
        "summary": "Gets one webhook subscription, with its signature secret.",
        "description": "The signature secret lets anyone forge deliveries; keep it server-side.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "description": "Identifier the platform assigned to the subscription.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Subscription returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A webhook subscription as stored, with the values the platform generated for it.",
                  "$ref": "#/components/schemas/WebHookWithId"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A webhook subscription as stored, with the values the platform generated for it.",
                  "$ref": "#/components/schemas/WebHookWithId"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A webhook subscription as stored, with the values the platform generated for it.",
                  "$ref": "#/components/schemas/WebHookWithId"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.webhook:read</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No subscription with this identifier, or the tenant does not exist.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.webhook:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "WebHook"
        ],
        "summary": "Replaces the editable fields of a webhook subscription. The identifier and signature secret are kept.",
        "description": "This is a full replacement, not a merge: an omitted `description` is cleared and an omitted\n`enabled` disables the subscription. The response has no body.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "description": "Identifier the platform assigned to the subscription.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The new description, events, endpoint and enabled state.",
          "content": {
            "application/json": {
              "schema": {
                "oneOf": [
                  {
                    "$ref": "#/components/schemas/WebHook"
                  },
                  {
                    "$ref": "#/components/schemas/WebHookWithId"
                  }
                ],
                "description": "The caller-editable part of a webhook subscription."
              }
            },
            "text/json": {
              "schema": {
                "oneOf": [
                  {
                    "$ref": "#/components/schemas/WebHook"
                  },
                  {
                    "$ref": "#/components/schemas/WebHookWithId"
                  }
                ],
                "description": "The caller-editable part of a webhook subscription."
              }
            },
            "application/*+json": {
              "schema": {
                "oneOf": [
                  {
                    "$ref": "#/components/schemas/WebHook"
                  },
                  {
                    "$ref": "#/components/schemas/WebHookWithId"
                  }
                ],
                "description": "The caller-editable part of a webhook subscription."
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Subscription updated."
          },
          "400": {
            "description": "Body missing, `events` empty or missing, or `endpoint` missing or not an absolute `http` or `https` URL.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.webhook:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No subscription with this identifier, or the tenant does not exist.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.webhook:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/tenants": {
      "get": {
        "tags": [
          "Tenant"
        ],
        "summary": "Lists every tenant of the platform with its status and purpose.",
        "description": "Restricted to the Global Administrator role. Not paged: every tenant is returned in one response. A\ntenant whose configuration cannot be read is listed as `onboarding` / `test`.",
        "responses": {
          "200": {
            "description": "Tenant directory entries returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "One tenant of the platform, as listed in the tenant directory.",
                    "$ref": "#/components/schemas/TenantDirectoryEntry"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "One tenant of the platform, as listed in the tenant directory.",
                    "$ref": "#/components/schemas/TenantDirectoryEntry"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "One tenant of the platform, as listed in the tenant directory.",
                    "$ref": "#/components/schemas/TenantDirectoryEntry"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller does not hold the <c>global:administrator</c> role.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [ ]
          }
        ]
      }
    },
    "/api/tenants/{tenantId}": {
      "delete": {
        "tags": [
          "Tenant"
        ],
        "summary": "Deletes every configuration file of the tenant, which removes the tenant from the platform.",
        "description": "Restricted to the Global Administrator role. Only configuration files are removed; passes and other\ntenant data are left in place. Tenant-scoped routes then answer 404, apart from `PUT`, which can\ncreate the tenant again.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "description": "Identifier of the tenant.",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Configuration deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller does not hold the <c>global:administrator</c> role.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant does not exist.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Tenant"
        ],
        "summary": "Downloads the tenant's configuration files as a zip archive, current or as of a past date.",
        "description": "The archive always includes the `.version` file, which records the version of each file; uploading\nthe archive back uses it to detect files changed on the server in the meantime. It is named\n`{yyyyMMdd-HHmmss}[-partial]-{tenantId}.fctwc`, from datetime or the current\ntime in UTC, with `-partial` when files is given. A files\nfilter that matches nothing returns an archive holding only `.version`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "description": "Identifier of the tenant.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "files",
            "in": "query",
            "description": "File paths to include, exact and case-sensitive, or with `*` as a wildcard\n            (`layouts/*`). Omitted, every file is included.",
            "schema": {
              "type": "array",
              "items": {
                "type": "string"
              }
            }
          },
          {
            "name": "datetime",
            "in": "query",
            "description": "Point in time to export the configuration as it was then. Omitted, the current\n            configuration is exported.",
            "schema": {
              "type": "string",
              "format": "date-time"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Configuration archive returned."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant does not exist or had no configuration at datetime.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "patch": {
        "tags": [
          "Tenant"
        ],
        "summary": "Adds, replaces or removes individual configuration files; files absent from the archive are kept.",
        "description": "Each archive entry replaces the server file at the same path; an empty entry deletes it. The resulting\nfull configuration is then saved as by `POST`, including validation unless\nforce is set.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "description": "Identifier of the tenant.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "force",
            "in": "query",
            "description": "`true` to save even when validation fails. Defaults to `false`.",
            "schema": {
              "type": "boolean"
            }
          }
        ],
        "requestBody": {
          "content": {
            "multipart/form-data": {
              "schema": {
                "type": "object",
                "properties": {
                  "file": {
                    "type": "string",
                    "description": "Zip archive (multipart form field `file`) of the files to change; an empty file removes\n            that path from the configuration.",
                    "format": "binary"
                  }
                }
              },
              "encoding": {
                "file": {
                  "style": "form"
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Configuration saved.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Identifies one state of a tenant's whole configuration: which files exist and when each was last written.",
                  "$ref": "#/components/schemas/TenantConfigurationVersionInformation"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Identifies one state of a tenant's whole configuration: which files exist and when each was last written.",
                  "$ref": "#/components/schemas/TenantConfigurationVersionInformation"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Identifies one state of a tenant's whole configuration: which files exist and when each was last written.",
                  "$ref": "#/components/schemas/TenantConfigurationVersionInformation"
                }
              }
            }
          },
          "400": {
            "description": "The file is missing, empty or not a zip archive, or the resulting configuration fails\n            validation (the errors are listed under `file`).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant does not exist.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Tenant"
        ],
        "summary": "Replaces the whole configuration of an existing tenant with the files of a zip archive.",
        "description": "Files that differ are written and server files absent from the archive are deleted. Unless\nforce is set, the configuration is validated first, and a file changed on the server\nsince the archive's `.version` was exported fails validation. The server keeps its own\n`.version`. Emits the tenant configuration updated event when anything changed.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "description": "Identifier of the tenant.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "force",
            "in": "query",
            "description": "`true` to save even when validation fails or files changed on the server.\n            Defaults to `false`.",
            "schema": {
              "type": "boolean"
            }
          }
        ],
        "requestBody": {
          "content": {
            "multipart/form-data": {
              "schema": {
                "type": "object",
                "properties": {
                  "file": {
                    "type": "string",
                    "description": "Zip archive (multipart form field `file`) holding every configuration file.",
                    "format": "binary"
                  }
                }
              },
              "encoding": {
                "file": {
                  "style": "form"
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Configuration saved.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Identifies one state of a tenant's whole configuration: which files exist and when each was last written.",
                  "$ref": "#/components/schemas/TenantConfigurationVersionInformation"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Identifies one state of a tenant's whole configuration: which files exist and when each was last written.",
                  "$ref": "#/components/schemas/TenantConfigurationVersionInformation"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Identifies one state of a tenant's whole configuration: which files exist and when each was last written.",
                  "$ref": "#/components/schemas/TenantConfigurationVersionInformation"
                }
              }
            }
          },
          "400": {
            "description": "The file is missing, empty or not a zip archive, or the configuration fails validation\n            (the errors are listed under `file`).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant does not exist; use `PUT` to create it.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Tenant"
        ],
        "summary": "Creates a tenant from a zip archive of its configuration files.",
        "description": "The only tenant-scoped route that accepts a tenantId that does not exist yet. The\nconfiguration is validated before anything is written, unless force is set.\nEntries under `__MACOSX`, `.DS_Store` files and folder entries are not imported.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "description": "Identifier of the new tenant.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "force",
            "in": "query",
            "description": "`true` to save even when validation fails. Defaults to `false`.",
            "schema": {
              "type": "boolean"
            }
          }
        ],
        "requestBody": {
          "content": {
            "multipart/form-data": {
              "schema": {
                "type": "object",
                "properties": {
                  "file": {
                    "type": "string",
                    "description": "Zip archive (multipart form field `file`) holding every configuration file.",
                    "format": "binary"
                  }
                }
              },
              "encoding": {
                "file": {
                  "style": "form"
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Tenant created.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Identifies one state of a tenant's whole configuration: which files exist and when each was last written.",
                  "$ref": "#/components/schemas/TenantConfigurationVersionInformation"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Identifies one state of a tenant's whole configuration: which files exist and when each was last written.",
                  "$ref": "#/components/schemas/TenantConfigurationVersionInformation"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Identifies one state of a tenant's whole configuration: which files exist and when each was last written.",
                  "$ref": "#/components/schemas/TenantConfigurationVersionInformation"
                }
              }
            }
          },
          "400": {
            "description": "The file is missing, empty or not a zip archive, or the configuration fails validation\n            (the errors are listed under `file`).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The tenant already exists.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/tenants/{tenantId}/{layoutId}": {
      "get": {
        "tags": [
          "Tenant"
        ],
        "summary": "Gets the configuration a front-end app boots with: the tenant's base configuration merged with the\nnamed layout, the layout winning on conflicts.",
        "description": "The response also carries the public settings the app needs (sign-in providers, locales, public\ndocuments, analytics and similar settings). A layout restricted to the tenant's redirect links is\nserved only to a page opened from one of those links; otherwise 401.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "description": "Identifier of the tenant.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "layoutId",
            "in": "path",
            "description": "Name of the layout, without file extension.",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Merged layout configuration returned.",
            "content": {
              "text/plain": {
                "schema": { }
              },
              "application/json": {
                "schema": { }
              },
              "text/json": {
                "schema": { }
              }
            }
          },
          "401": {
            "description": "The layout is restricted to the tenant's redirect links and the page was not opened from one.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant does not exist, or it has no such layout.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/tenants/{tenantId}/config/history": {
      "get": {
        "tags": [
          "Tenant"
        ],
        "summary": "Lists the saved versions of the tenant configuration, newest first, with the files each one changed and\nwho saved it.",
        "description": "Each entry's user is resolved to a display name and email when the user still exists; a change made with\nan API key shows as `API Key - {key name}`. With files, only versions that changed\na matching file are listed and `total` counts those.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "description": "Identifier of the tenant.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "files",
            "in": "query",
            "description": "File paths to filter on, case-insensitive, exact or with `*` as a wildcard.\n            Omitted, every version is listed.",
            "schema": {
              "type": "array",
              "items": {
                "type": "string"
              }
            }
          },
          {
            "name": "offset",
            "in": "query",
            "description": "Number of versions to skip, 0 or more; negative returns 400. Defaults to 0.",
            "schema": {
              "type": "integer",
              "format": "int32",
              "default": 0
            }
          },
          {
            "name": "limit",
            "in": "query",
            "description": "Maximum number of versions to return, 1 or more; 0 or less returns 400. Defaults to\n            50.",
            "schema": {
              "type": "integer",
              "format": "int32",
              "default": 50
            }
          }
        ],
        "responses": {
          "200": {
            "description": "History returned; possibly empty.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "One page of the saved versions of a tenant's configuration, newest first.",
                  "$ref": "#/components/schemas/TenantConfigurationHistoryPage"
                }
              },
              "application/json": {
                "schema": {
                  "description": "One page of the saved versions of a tenant's configuration, newest first.",
                  "$ref": "#/components/schemas/TenantConfigurationHistoryPage"
                }
              },
              "text/json": {
                "schema": {
                  "description": "One page of the saved versions of a tenant's configuration, newest first.",
                  "$ref": "#/components/schemas/TenantConfigurationHistoryPage"
                }
              }
            }
          },
          "400": {
            "description": "offset is negative or limit is not positive.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant does not exist.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/tenants/{tenantId}/test": {
      "get": {
        "tags": [
          "Tenant"
        ],
        "summary": "Runs every configuration check against the tenant's current configuration, and tells an authenticated\nback-office caller who the platform sees it as.",
        "description": "On success the body is `tenantId` and `user`: a back-office caller's `userName`,\n`roles` and `permissions`, otherwise `null`. On failure a back-office caller gets the\nerror list under the empty key of `errors`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "description": "Identifier of the tenant.",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Configuration valid."
          },
          "400": {
            "description": "Configuration invalid; the errors are listed for a back-office caller.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The credentials sent are invalid.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant does not exist.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [ ]
          },
          {
            "apiKey": [ ]
          },
          { }
        ]
      }
    },
    "/api/warmup": {
      "get": {
        "tags": [
          "Warmup"
        ],
        "summary": "Prepares every tenant, one tenant after the other, and answers once all are done.",
        "description": "One warmup runs at a time: a call that cannot start within a few seconds returns 409. A 200 means every\ntenant has been attempted, not that every tenant is ready. Duration grows with the number of tenants.",
        "responses": {
          "200": {
            "description": "Every tenant has been attempted."
          },
          "409": {
            "description": "Another warmup is still running.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/admin/apiKeys": {
      "get": {
        "tags": [
          "ApiKeys"
        ],
        "summary": "List API keys for the tenant",
        "description": "Returns every API key, ordered by name. Key values are never included in responses.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "API keys returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "oneOf": [
                      {
                        "description": "API key definition returned by list and get endpoints.\nThe key value itself is never returned.",
                        "$ref": "#/components/schemas/ApiKeyDefinition"
                      },
                      {
                        "$ref": "#/components/schemas/ApiKeyCreatedResponse"
                      }
                    ],
                    "description": "API key definition returned by list and get endpoints.\nThe key value itself is never returned."
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "oneOf": [
                      {
                        "$ref": "#/components/schemas/ApiKeyDefinition"
                      },
                      {
                        "$ref": "#/components/schemas/ApiKeyCreatedResponse"
                      }
                    ],
                    "description": "API key definition returned by list and get endpoints.\nThe key value itself is never returned."
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "oneOf": [
                      {
                        "$ref": "#/components/schemas/ApiKeyDefinition"
                      },
                      {
                        "$ref": "#/components/schemas/ApiKeyCreatedResponse"
                      }
                    ],
                    "description": "API key definition returned by list and get endpoints.\nThe key value itself is never returned."
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.apiKey:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.apiKey:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "ApiKeys"
        ],
        "summary": "Create a new API key",
        "description": "Generates a 64-character key and returns it in plaintext in the response.\n**The token is only returned once — copy it immediately.** A lost token cannot be recovered: delete the\nkey and create a new one.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Name, initial state and permissions of the new key.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to create an API key.",
                "$ref": "#/components/schemas/CreateApiKeyRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to create an API key.",
                "$ref": "#/components/schemas/CreateApiKeyRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to create an API key.",
                "$ref": "#/components/schemas/CreateApiKeyRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "201": {
            "description": "API key created. Response includes the one-time plaintext token.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Returned once after a successful key creation.\nThe `Token` field contains the plaintext API key and will never be retrievable again.",
                  "$ref": "#/components/schemas/ApiKeyCreatedResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Returned once after a successful key creation.\nThe `Token` field contains the plaintext API key and will never be retrievable again.",
                  "$ref": "#/components/schemas/ApiKeyCreatedResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Returned once after a successful key creation.\nThe `Token` field contains the plaintext API key and will never be retrievable again.",
                  "$ref": "#/components/schemas/ApiKeyCreatedResponse"
                }
              }
            }
          },
          "400": {
            "description": "Name is missing, too long or has a forbidden character, or permissions are missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.apiKey:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "A key with this name already exists, in any case.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.apiKey:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/apiKeys/{keyName}": {
      "delete": {
        "tags": [
          "ApiKeys"
        ],
        "summary": "Delete an API key",
        "description": "Removes the API key. Requests made with it are refused from then on; there is no undo.",
        "parameters": [
          {
            "name": "keyName",
            "in": "path",
            "description": "Name of the key, matched case-insensitively.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "API key deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.apiKey:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "API key not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.apiKey:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "ApiKeys"
        ],
        "summary": "Get a specific API key",
        "description": "Returns the API key definition identified by keyName.\nThe key value is never returned.",
        "parameters": [
          {
            "name": "keyName",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "API key returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ApiKeyDefinition"
                    },
                    {
                      "$ref": "#/components/schemas/ApiKeyCreatedResponse"
                    }
                  ],
                  "description": "API key definition returned by list and get endpoints.\nThe key value itself is never returned."
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ApiKeyDefinition"
                    },
                    {
                      "$ref": "#/components/schemas/ApiKeyCreatedResponse"
                    }
                  ],
                  "description": "API key definition returned by list and get endpoints.\nThe key value itself is never returned."
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ApiKeyDefinition"
                    },
                    {
                      "$ref": "#/components/schemas/ApiKeyCreatedResponse"
                    }
                  ],
                  "description": "API key definition returned by list and get endpoints.\nThe key value itself is never returned."
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.apiKey:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "API key not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.apiKey:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "ApiKeys"
        ],
        "summary": "Update an API key",
        "description": "Replaces the `enabled` and `permissions` fields of the key.\nThe key name and the key value are not changed.",
        "parameters": [
          {
            "name": "keyName",
            "in": "path",
            "description": "Name of the key, matched case-insensitively.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "State and permissions replacing the current ones.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to update an API key.",
                "$ref": "#/components/schemas/UpdateApiKeyRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to update an API key.",
                "$ref": "#/components/schemas/UpdateApiKeyRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to update an API key.",
                "$ref": "#/components/schemas/UpdateApiKeyRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "API key updated.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ApiKeyDefinition"
                    },
                    {
                      "$ref": "#/components/schemas/ApiKeyCreatedResponse"
                    }
                  ],
                  "description": "API key definition returned by list and get endpoints.\nThe key value itself is never returned."
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ApiKeyDefinition"
                    },
                    {
                      "$ref": "#/components/schemas/ApiKeyCreatedResponse"
                    }
                  ],
                  "description": "API key definition returned by list and get endpoints.\nThe key value itself is never returned."
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ApiKeyDefinition"
                    },
                    {
                      "$ref": "#/components/schemas/ApiKeyCreatedResponse"
                    }
                  ],
                  "description": "API key definition returned by list and get endpoints.\nThe key value itself is never returned."
                }
              }
            }
          },
          "400": {
            "description": "Permissions are missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.apiKey:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "API key not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.apiKey:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/benefitTemplates": {
      "get": {
        "tags": [
          "BenefitTemplates"
        ],
        "summary": "List all configured benefit templates.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Benefit templates returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                    "$ref": "#/components/schemas/BenefitTemplate"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                    "$ref": "#/components/schemas/BenefitTemplate"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                    "$ref": "#/components/schemas/BenefitTemplate"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.benefitTemplate:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.benefitTemplate:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "BenefitTemplates"
        ],
        "summary": "Create a new benefit template.",
        "description": "The benefit template id must be unique within the tenant; returns 409 if it already exists.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Benefit template payload.",
          "content": {
            "application/json": {
              "schema": {
                "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                "$ref": "#/components/schemas/BenefitTemplate"
              }
            },
            "text/json": {
              "schema": {
                "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                "$ref": "#/components/schemas/BenefitTemplate"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                "$ref": "#/components/schemas/BenefitTemplate"
              }
            }
          },
          "required": true
        },
        "responses": {
          "201": {
            "description": "Benefit template created.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                  "$ref": "#/components/schemas/BenefitTemplate"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                  "$ref": "#/components/schemas/BenefitTemplate"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                  "$ref": "#/components/schemas/BenefitTemplate"
                }
              }
            }
          },
          "400": {
            "description": "Invalid payload.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.benefitTemplate:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "A benefit template with the same id already exists, or another benefit template write is in progress.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.benefitTemplate:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/benefitTemplates/{id}": {
      "delete": {
        "tags": [
          "BenefitTemplates"
        ],
        "summary": "Delete a benefit template.",
        "description": "Refused while any benefit issued from the benefit template is still live: wait for those benefits to\nexpire or delete them first. Also refused while an enabled automation grants it.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "description": "Benefit template identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Benefit template deleted."
          },
          "400": {
            "description": "Invalid benefit template id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.benefitTemplate:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Benefit template not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The benefit template still has live benefits or is granted by an enabled automation, or another benefit template write is in progress.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.benefitTemplate:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "BenefitTemplates"
        ],
        "summary": "Retrieve a single benefit template by id.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "description": "Benefit template identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Benefit template returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                  "$ref": "#/components/schemas/BenefitTemplate"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                  "$ref": "#/components/schemas/BenefitTemplate"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                  "$ref": "#/components/schemas/BenefitTemplate"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.benefitTemplate:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Benefit template not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.benefitTemplate:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "BenefitTemplates"
        ],
        "summary": "Update an existing benefit template.",
        "description": "Benefits already issued keep what they were given unless updateBenefits is set. Then\nevery live, still redeemable benefit is rewritten from the new definition after the response, and the\npasses showing them are updated. A rewrite replaces whatever the benefit\ntemplate carries, including an edit made on one benefit; movements, creation date and code are kept.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "description": "Benefit template identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "updateBenefits",
            "in": "query",
            "description": "Also rewrite the live benefits issued from this benefit template.",
            "schema": {
              "type": "boolean"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Updated payload. The id in the route wins over the body.",
          "content": {
            "application/json": {
              "schema": {
                "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                "$ref": "#/components/schemas/BenefitTemplate"
              }
            },
            "text/json": {
              "schema": {
                "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                "$ref": "#/components/schemas/BenefitTemplate"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                "$ref": "#/components/schemas/BenefitTemplate"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Benefit template updated.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                  "$ref": "#/components/schemas/BenefitTemplate"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                  "$ref": "#/components/schemas/BenefitTemplate"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant.",
                  "$ref": "#/components/schemas/BenefitTemplate"
                }
              }
            }
          },
          "400": {
            "description": "Invalid payload, or benefits asked to be updated while the benefit template changes its pass template.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.benefitTemplate:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Benefit template not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "Another benefit template write is in progress; retry.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.benefitTemplate:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/benefitTemplates/{id}/images": {
      "post": {
        "tags": [
          "BenefitTemplates"
        ],
        "summary": "Upload an image file for a benefit template.",
        "description": "The returned `path` is the value to store in the benefit template's appearance fields. A file name\nstarts with a letter or a digit, uses only letters, digits, `-` and `_`, and ends in\n`.png`, `.jpg`, `.jpeg`, `.gif` or `.webp` (`hero.png`); uploading the same\nname again replaces the image. The content must be an image matching that extension.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "description": "Benefit template identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "multipart/form-data": {
              "schema": {
                "type": "object",
                "properties": {
                  "file": {
                    "type": "string",
                    "description": "Image file (multipart/form-data), at most 8 MB.",
                    "format": "binary"
                  }
                }
              },
              "encoding": {
                "file": {
                  "style": "form"
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Image uploaded; returns the image path.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Holds the path and file name of a benefit template image.",
                  "$ref": "#/components/schemas/BenefitTemplateImageInfo"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Holds the path and file name of a benefit template image.",
                  "$ref": "#/components/schemas/BenefitTemplateImageInfo"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Holds the path and file name of a benefit template image.",
                  "$ref": "#/components/schemas/BenefitTemplateImageInfo"
                }
              }
            }
          },
          "400": {
            "description": "Missing or empty file, invalid benefit template id or file name, or content that is not the image its extension declares.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.benefitTemplate:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Benefit template not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "413": {
            "description": "The image is larger than 8 MB.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.benefitTemplate:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/benefitTemplates/{id}/images/{fileName}": {
      "get": {
        "tags": [
          "BenefitTemplates"
        ],
        "summary": "Retrieve the bytes of a specific benefit template image.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "description": "Benefit template identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "fileName",
            "in": "path",
            "description": "Image file name (e.g. `hero.png`).",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Image bytes returned."
          },
          "400": {
            "description": "Invalid benefit template id or file name.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.benefitTemplate:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Image not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.benefitTemplate:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/config": {
      "get": {
        "tags": [
          "Config"
        ],
        "summary": "Get tenant core configuration",
        "description": "Returns the tenant name, favicon URLs, effective public URI, enabled extensions, and tenant language settings.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Configuration returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Tenant core configuration response",
                  "$ref": "#/components/schemas/TenantConfigWeb"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Tenant core configuration response",
                  "$ref": "#/components/schemas/TenantConfigWeb"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Tenant core configuration response",
                  "$ref": "#/components/schemas/TenantConfigWeb"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.core:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.core:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "patch": {
        "tags": [
          "Config"
        ],
        "summary": "Update tenant core configuration",
        "description": "Updates editable core fields of the tenant configuration.\nStatus and purpose can only be modified by global administrators.\nAn uploaded favicon file replaces the favicon of its slot, and the matching URL field then points to it,\noverriding any URL sent for the same slot.\nRemoving a language from `availableLanguages` deletes every translation of the tenant in that\nlanguage.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "multipart/form-data": {
              "schema": {
                "type": "object",
                "properties": {
                  "LogoUrl": {
                    "type": "string",
                    "description": "Logo URL. Omitted or empty keeps the current value; it cannot be cleared through this endpoint."
                  },
                  "FaviconUrl": {
                    "type": "string",
                    "description": "Small (48x48) favicon URL. Omitted or empty keeps the current value. Ignored when Neo.Web.Api.Admin.Controllers.UpdateTenantConfigWebRequest.Favicon\nis sent."
                  },
                  "LargeFaviconUrl": {
                    "type": "string",
                    "description": "Large (192x192) favicon URL. Omitted keeps the current value, an empty string clears it. Ignored when\nNeo.Web.Api.Admin.Controllers.UpdateTenantConfigWebRequest.LargeFavicon is sent."
                  },
                  "AppleFaviconUrl": {
                    "type": "string",
                    "description": "Apple touch icon (180x180) URL. Omitted keeps the current value, an empty string clears it. Ignored when\nNeo.Web.Api.Admin.Controllers.UpdateTenantConfigWebRequest.AppleFavicon is sent."
                  },
                  "Favicon": {
                    "type": "string",
                    "description": "Small (48x48) favicon file. Must be non-empty with a `.png`, `.jpg`, `.jpeg`, `.gif`\nor `.ico` extension, else 400.",
                    "format": "binary"
                  },
                  "LargeFavicon": {
                    "type": "string",
                    "description": "Large (192x192) favicon file. Same file rules as\nNeo.Web.Api.Admin.Controllers.UpdateTenantConfigWebRequest.Favicon.",
                    "format": "binary"
                  },
                  "AppleFavicon": {
                    "type": "string",
                    "description": "Apple touch icon (180x180) file. Same file rules as\nNeo.Web.Api.Admin.Controllers.UpdateTenantConfigWebRequest.Favicon.",
                    "format": "binary"
                  },
                  "AppTitle": {
                    "type": "string",
                    "description": "Title replacing the default application title in the browser. Omitted keeps the current value, an empty\nstring clears it."
                  },
                  "DefaultLanguage": {
                    "type": "string",
                    "description": "Fallback language of the tenant. Must be one of the available languages after this update\n(case-insensitive), else 400. Omitted keeps the current value."
                  },
                  "AvailableLanguages": {
                    "type": "array",
                    "items": {
                      "type": "string"
                    },
                    "description": "Languages the tenant's content is offered in; replaces the whole list. Must not be empty, else 400.\nOmitted keeps the current list."
                  },
                  "Status": {
                    "description": "Lifecycle status of the tenant. Omitted keeps the current value. Changing it requires the global\nadministrator role, else 403; resending the current value is accepted from anyone.",
                    "$ref": "#/components/schemas/TenantStatus"
                  },
                  "Purpose": {
                    "description": "What the tenant is used for. Omitted keeps the current value. Changing it requires the global\nadministrator role, else 403; resending the current value is accepted from anyone.",
                    "$ref": "#/components/schemas/TenantPurpose"
                  }
                }
              },
              "encoding": {
                "LogoUrl": {
                  "style": "form"
                },
                "FaviconUrl": {
                  "style": "form"
                },
                "LargeFaviconUrl": {
                  "style": "form"
                },
                "AppleFaviconUrl": {
                  "style": "form"
                },
                "Favicon": {
                  "style": "form"
                },
                "LargeFavicon": {
                  "style": "form"
                },
                "AppleFavicon": {
                  "style": "form"
                },
                "AppTitle": {
                  "style": "form"
                },
                "DefaultLanguage": {
                  "style": "form"
                },
                "AvailableLanguages": {
                  "style": "form"
                },
                "Status": {
                  "style": "form"
                },
                "Purpose": {
                  "style": "form"
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Configuration updated and returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Tenant core configuration response",
                  "$ref": "#/components/schemas/TenantConfigWeb"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Tenant core configuration response",
                  "$ref": "#/components/schemas/TenantConfigWeb"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Tenant core configuration response",
                  "$ref": "#/components/schemas/TenantConfigWeb"
                }
              }
            }
          },
          "400": {
            "description": "Empty `availableLanguages`, a `defaultLanguage` missing from the available languages, or an empty favicon file or one with an unsupported extension.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "Status or purpose changed by a caller who is not a global administrator.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The tenant configuration changed since it was read; nothing was written.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "413": {
            "description": "The request body is larger than 8 MB.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.general:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/configuration/schemas": {
      "get": {
        "tags": [
          "ConfigSchemas"
        ],
        "summary": "Returns every configuration schema and the files it validates.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Schema catalogue returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The tenant configuration schemas, and which file each of them validates.",
                  "$ref": "#/components/schemas/ConfigSchemaCatalog"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The tenant configuration schemas, and which file each of them validates.",
                  "$ref": "#/components/schemas/ConfigSchemaCatalog"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The tenant configuration schemas, and which file each of them validates.",
                  "$ref": "#/components/schemas/ConfigSchemaCatalog"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.tools:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.tools:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/configuration/script-typings": {
      "get": {
        "tags": [
          "ScriptTypings"
        ],
        "summary": "Returns the script type declarations, and the same endpoints as data.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Typings returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "What an editor needs to help someone write an extensibility script.",
                  "$ref": "#/components/schemas/ScriptTypings"
                }
              },
              "application/json": {
                "schema": {
                  "description": "What an editor needs to help someone write an extensibility script.",
                  "$ref": "#/components/schemas/ScriptTypings"
                }
              },
              "text/json": {
                "schema": {
                  "description": "What an editor needs to help someone write an extensibility script.",
                  "$ref": "#/components/schemas/ScriptTypings"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.tools:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.tools:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/customdomain": {
      "delete": {
        "tags": [
          "CustomDomain"
        ],
        "summary": "Remove the domain",
        "description": "Puts the tenant back on the platform's own address, then releases the hostname.\n            \nRequires `confirm=true`, because for a live domain this reverts every customer-facing URL.",
        "parameters": [
          {
            "name": "confirm",
            "in": "query",
            "description": "Must be `true`; acknowledges that a live domain's customer-facing URLs revert.",
            "schema": {
              "type": "boolean"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Domain removed."
          },
          "400": {
            "description": "The confirmation flag was not passed.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.customDomain:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "This tenant has no custom domain.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "503": {
            "description": "Custom domain provisioning is not configured on this environment.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.customDomain:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "CustomDomain"
        ],
        "summary": "Get the tenant's custom domain",
        "description": "The state is current on every read, so a domain the customer fixed days later reports correctly with no\nother call. Reading changes nothing.\n            \nWhen the state cannot be checked the record still comes back, with a null `lastCheckedAt` — do\nnot read certificate health from such a record. A null `isBoundInAzure` likewise means unknown,\nnot a confirmed absence.\n            \n`diagnostics` is populated for global administrators only.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The tenant's custom domain.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "One custom domain, as the admin API reports it.",
                  "$ref": "#/components/schemas/CustomDomainRecord"
                }
              },
              "application/json": {
                "schema": {
                  "description": "One custom domain, as the admin API reports it.",
                  "$ref": "#/components/schemas/CustomDomainRecord"
                }
              },
              "text/json": {
                "schema": {
                  "description": "One custom domain, as the admin API reports it.",
                  "$ref": "#/components/schemas/CustomDomainRecord"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.customDomain:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "This tenant has no custom domain.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "503": {
            "description": "Custom domain provisioning is not configured on this environment.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.customDomain:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "CustomDomain"
        ],
        "summary": "Claim a domain",
        "description": "Registers the hostname and records it as claimed. **Nothing about\nthe tenant's public address changes** — that needs a separate call to `activate`.\n            \nRefused with 409 when the tenant already has a different domain: a tenant has one public address, so\nreplace a domain by removing it, then adding the new one.\n            \nRoot domains are accepted; they need a DNS provider that can flatten them (CNAME flattening, ALIAS or\nANAME), which is the customer's to check. Wildcards are rejected.\n            \nCall `GET preflight` first if you need to know *why* a hostname is unusable — this action reports\na rejection as a 400 for a human to read, not as codes to branch on.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The hostname to claim.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to claim a domain.",
                "$ref": "#/components/schemas/AddCustomDomainRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to claim a domain.",
                "$ref": "#/components/schemas/AddCustomDomainRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to claim a domain.",
                "$ref": "#/components/schemas/AddCustomDomainRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "201": {
            "description": "Domain claimed. The response says which DNS records the customer must create.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "One custom domain, as the admin API reports it.",
                  "$ref": "#/components/schemas/CustomDomainRecord"
                }
              },
              "application/json": {
                "schema": {
                  "description": "One custom domain, as the admin API reports it.",
                  "$ref": "#/components/schemas/CustomDomainRecord"
                }
              },
              "text/json": {
                "schema": {
                  "description": "One custom domain, as the admin API reports it.",
                  "$ref": "#/components/schemas/CustomDomainRecord"
                }
              }
            }
          },
          "400": {
            "description": "The hostname cannot be used.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.customDomain:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The hostname is already in use, or this tenant already has a domain.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "502": {
            "description": "A provider did not answer. Nothing was changed; the call is worth retrying.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "503": {
            "description": "Custom domain provisioning is not configured on this environment.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.customDomain:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/customdomain/activate": {
      "post": {
        "tags": [
          "CustomDomain"
        ],
        "summary": "Switch the tenant's public address to the domain",
        "description": "The only call that changes what customers see: sets the tenant's `publicUri` to the domain.\n            \nRefused unless the domain is ready **and** a check has passed for it recently.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The tenant's public address now points at the domain.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "One custom domain, as the admin API reports it.",
                  "$ref": "#/components/schemas/CustomDomainRecord"
                }
              },
              "application/json": {
                "schema": {
                  "description": "One custom domain, as the admin API reports it.",
                  "$ref": "#/components/schemas/CustomDomainRecord"
                }
              },
              "text/json": {
                "schema": {
                  "description": "One custom domain, as the admin API reports it.",
                  "$ref": "#/components/schemas/CustomDomainRecord"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.customDomain:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "No domain, or it is not ready, or it has not passed a recent check.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "503": {
            "description": "Custom domain provisioning is not configured on this environment.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.customDomain:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/customdomain/check": {
      "post": {
        "tags": [
          "CustomDomain"
        ],
        "summary": "Check that the domain reaches this application",
        "description": "Calls the hostname from the outside and confirms the request arrives here identified as that hostname.\nOne call exercises the customer's DNS, the certificate, and the platform accepting the hostname.\n            \nExpected to fail while the customer still has records to add — the failure code says which link in the\nchain is broken, which is the point of running it early.\n            \nRequires the **write** scope: the check can complete the domain's setup before testing it.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Check ran. The body says whether it passed and, if not, why.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Outcome of one configuration check.",
                  "$ref": "#/components/schemas/CustomDomainProbeResult"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Outcome of one configuration check.",
                  "$ref": "#/components/schemas/CustomDomainProbeResult"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Outcome of one configuration check.",
                  "$ref": "#/components/schemas/CustomDomainProbeResult"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.customDomain:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "This tenant has no custom domain.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "503": {
            "description": "Custom domain provisioning is not configured on this environment.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.customDomain:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/customdomain/preflight": {
      "get": {
        "tags": [
          "CustomDomain"
        ],
        "summary": "Check a hostname before claiming it",
        "description": "Answers the two questions the add screen cannot answer on its own: whether the hostname is already in\nuse, and — for a root domain — whether the customer's DNS provider can even point it at us. Creates\nnothing and writes nothing.\n            \nThe apex verdict is correct for `brand.co.uk` and for a delegated subzone.\n            \nAn invalid hostname is still a 200: the point is to report what is wrong with it, in codes the caller\ncan translate.",
        "parameters": [
          {
            "name": "hostname",
            "in": "query",
            "description": "Hostname the customer intends to claim, for example `registration.brand.com`.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Preflight completed. A hostname may be invalid and still return 200.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "What a preflight found out about a hostname.",
                  "$ref": "#/components/schemas/CustomDomainPreflight"
                }
              },
              "application/json": {
                "schema": {
                  "description": "What a preflight found out about a hostname.",
                  "$ref": "#/components/schemas/CustomDomainPreflight"
                }
              },
              "text/json": {
                "schema": {
                  "description": "What a preflight found out about a hostname.",
                  "$ref": "#/components/schemas/CustomDomainPreflight"
                }
              }
            }
          },
          "400": {
            "description": "`hostname` is missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.customDomain:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "503": {
            "description": "Custom domain provisioning is not configured on this environment.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.customDomain:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/downloadPages": {
      "get": {
        "tags": [
          "DownloadPages"
        ],
        "summary": "List wallet download pages for the tenant",
        "description": "Returns every `pass`, `passList` and `benefitList` page of the tenant, ordered by name.\n            \nA page whose stored YAML cannot be read is left out; reading it by name reports the problem.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Download pages returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Download page returned by the list endpoint.",
                    "$ref": "#/components/schemas/DownloadPageListItem"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Download page returned by the list endpoint.",
                    "$ref": "#/components/schemas/DownloadPageListItem"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Download page returned by the list endpoint.",
                    "$ref": "#/components/schemas/DownloadPageListItem"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.passType:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.passType:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/downloadPages/{name}": {
      "delete": {
        "tags": [
          "DownloadPages"
        ],
        "summary": "Delete a wallet download page",
        "description": "Removes the page, and its own translation directory when no other page or pass template reads from it.\n            \n## This breaks passes that are already in customers' wallets\n            \nA download page is served publicly at `/{tenantId}/{name}`. Every QR code, campaign link,\npartner link and short link pointing at that URL stops working.\n            \nThe deletion is refused with a conflict while:\n            \n- a pass template lands on the page. A template names its page through `passLayoutName`, and a\n  template that names none lands on `pass` — so the page called `pass` cannot be deleted\n  while any template leaves the property unset.\n- another layout uses the page as its `errorLayoutName`, or sends customers to it once\n  registration completes.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Page name, the last segment of its public URL `/{tenantId}/{name}`.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Download page deleted. Its public URL now returns 404."
          },
          "400": {
            "description": "The name is not valid: 1 to 100 letters, digits, underscores, hyphens, dots or spaces.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.passType:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No layout of that name, or the layout is not a download page.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "A pass template or another layout still points at the page (type `#download-page-in-use`), or a\npage or template that would say so cannot be read (type `#unreadable-configuration-file`).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.passType:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "DownloadPages"
        ],
        "summary": "Get a wallet download page",
        "description": "Returns the modelled properties of the page, its translations for every culture that has any, and\nthe page as YAML, verbatim, in `yaml`.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Page name, the last segment of its public URL `/{tenantId}/{name}`.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Download page returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of a download page, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/DownloadPageDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of a download page, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/DownloadPageDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of a download page, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/DownloadPageDefinition"
                }
              }
            }
          },
          "400": {
            "description": "The name is not valid: 1 to 100 letters, digits, underscores, hyphens, dots or spaces.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.passType:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No layout of that name, or the layout is not a `pass`, `passList` or `benefitList` page.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The stored page cannot be read (type `#unreadable-configuration-file`).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.passType:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "DownloadPages"
        ],
        "summary": "Create or replace a wallet download page",
        "description": "The name in the route is the page's identity and the last segment of its public URL: the caller\nchooses it, and the page is created when none exists under the name. Repeating the same request\nleaves the same page behind, so a retry after a lost response is safe.\n            \n`type` is required to create and cannot be changed afterwards. Neither can the page be renamed,\nbecause its name is its public URL.\n            \nA page whose stored YAML can no longer be read cannot be saved here by either path; it has to be\nrepaired in the Advanced Configuration editor.\n            \n`If-None-Match: *` restricts the request to creating: a page already stored under the name is\nrefused rather than replaced. Without it a caller that needs to know whether it created or replaced\nreads the status code.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Page name, the last segment of its public URL `/{tenantId}/{name}`. A new page's name is 1 to 50\nletters, digits, hyphens or underscores; an existing page may keep a name outside these rules.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The page properties to write, or the whole page as YAML through `yaml`.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to create or replace a download page.",
                "$ref": "#/components/schemas/SaveDownloadPageRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to create or replace a download page.",
                "$ref": "#/components/schemas/SaveDownloadPageRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to create or replace a download page.",
                "$ref": "#/components/schemas/SaveDownloadPageRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Download page replaced.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of a download page, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/DownloadPageDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of a download page, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/DownloadPageDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of a download page, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/DownloadPageDefinition"
                }
              }
            }
          },
          "201": {
            "description": "Download page created.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of a download page, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/DownloadPageDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of a download page, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/DownloadPageDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of a download page, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/DownloadPageDefinition"
                }
              }
            }
          },
          "400": {
            "description": "The name, kind, flow or a culture code is invalid, `yaml` is sent with typed fields, a property\ndoes not apply to the page's kind, or the resulting configuration fails validation.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.passType:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The stored page cannot be read (type `#unreadable-configuration-file`), or the name is held by a layout that is not a download page (type `#conflict`).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "412": {
            "description": "A page of that name exists and the request asked to create only (type `#name-already-taken`).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.passType:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/emailProvider": {
      "get": {
        "tags": [
          "EmailProvider"
        ],
        "summary": "Get email provider settings",
        "description": "Returns the email provider together with the content of its script.\nA tenant with no email provider configured yet gets a definition with a null `type`.\nThe API key is never returned; `hasApiKey` indicates whether one is currently set. Omit\n`apiKey` on `PUT` to keep the currently configured key.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Settings returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Email provider settings. The API key is never returned.",
                  "$ref": "#/components/schemas/EmailProviderDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Email provider settings. The API key is never returned.",
                  "$ref": "#/components/schemas/EmailProviderDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Email provider settings. The API key is never returned.",
                  "$ref": "#/components/schemas/EmailProviderDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.email:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.email:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "EmailProvider"
        ],
        "summary": "Configure email provider settings",
        "description": "Replaces the email provider.\n            \nThe script is only saved when `type` is `script`, so switching to another provider\nkeeps the current script available to switch back to.\n            \nSwitching to a different provider type drops the previous provider's API key and custom sending domain.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The provider to use and its settings.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to configure the email provider.",
                "$ref": "#/components/schemas/UpdateEmailProviderRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to configure the email provider.",
                "$ref": "#/components/schemas/UpdateEmailProviderRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to configure the email provider.",
                "$ref": "#/components/schemas/UpdateEmailProviderRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Settings updated; the body is the new state, as `GET` returns it.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Email provider settings. The API key is never returned.",
                  "$ref": "#/components/schemas/EmailProviderDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Email provider settings. The API key is never returned.",
                  "$ref": "#/components/schemas/EmailProviderDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Email provider settings. The API key is never returned.",
                  "$ref": "#/components/schemas/EmailProviderDefinition"
                }
              }
            }
          },
          "400": {
            "description": "Unknown `type`, an invalid sender address or name, or the sender identity, the API key or the script is missing and none is currently configured.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.email:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.email:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/emailTemplates": {
      "get": {
        "tags": [
          "EmailTemplates"
        ],
        "summary": "List email templates for the tenant",
        "description": "Returns every template id along with the cultures it has design content for, sorted by id.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Email templates returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Email template returned by the list endpoint.",
                    "$ref": "#/components/schemas/EmailTemplateListItem"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Email template returned by the list endpoint.",
                    "$ref": "#/components/schemas/EmailTemplateListItem"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Email template returned by the list endpoint.",
                    "$ref": "#/components/schemas/EmailTemplateListItem"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.emailTemplate:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.emailTemplate:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "EmailTemplates"
        ],
        "summary": "Create a new email template",
        "description": "Creates the design source (and, if provided, the compiled subject/body) for one or more cultures of a\nnew template. To duplicate an existing template, `GET` its content first and `POST` it back\nunder a new id here — there is no dedicated duplicate endpoint. To add a culture to an existing\ntemplate, use `PUT`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Identifier and content of the new template.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to create a new email template.",
                "$ref": "#/components/schemas/CreateEmailTemplateRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to create a new email template.",
                "$ref": "#/components/schemas/CreateEmailTemplateRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to create a new email template.",
                "$ref": "#/components/schemas/CreateEmailTemplateRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "201": {
            "description": "Email template created.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of an email template, returned by get/create/save endpoints.",
                  "$ref": "#/components/schemas/EmailTemplateDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of an email template, returned by get/create/save endpoints.",
                  "$ref": "#/components/schemas/EmailTemplateDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of an email template, returned by get/create/save endpoints.",
                  "$ref": "#/components/schemas/EmailTemplateDefinition"
                }
              }
            }
          },
          "400": {
            "description": "Id or culture is invalid, no culture was provided, or a culture has a subject without a body or a body without a subject.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.emailTemplate:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "A template with this id already exists.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.emailTemplate:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/emailTemplates/{id}": {
      "delete": {
        "tags": [
          "EmailTemplates"
        ],
        "summary": "Delete an email template",
        "description": "Deletes the design source and compiled subject/body for the specified culture. When\nculture is omitted, deletes every culture of the template.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "description": "Template identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "culture",
            "in": "query",
            "description": "Culture code to delete; omitted deletes the whole template.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Email template (or culture) deleted."
          },
          "400": {
            "description": "Culture is invalid.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.emailTemplate:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Email template (or culture) not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.emailTemplate:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "EmailTemplates"
        ],
        "summary": "Get an email template",
        "description": "Returns the design source (HTML/CSS) and, when available, the compiled subject/body for every culture\nof the template identified by id.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "description": "Template identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Email template returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of an email template, returned by get/create/save endpoints.",
                  "$ref": "#/components/schemas/EmailTemplateDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of an email template, returned by get/create/save endpoints.",
                  "$ref": "#/components/schemas/EmailTemplateDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of an email template, returned by get/create/save endpoints.",
                  "$ref": "#/components/schemas/EmailTemplateDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.emailTemplate:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No culture of this template has a design source.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.emailTemplate:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "EmailTemplates"
        ],
        "summary": "Save an email template",
        "description": "Upserts the design source (and, if provided, the compiled subject/body) for one or more cultures of an\nexisting template. Cultures not present in the request body are left untouched.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "description": "Template identifier.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Content to write, per culture.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to save (create or update) culture content on an existing email template.",
                "$ref": "#/components/schemas/SaveEmailTemplateRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to save (create or update) culture content on an existing email template.",
                "$ref": "#/components/schemas/SaveEmailTemplateRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to save (create or update) culture content on an existing email template.",
                "$ref": "#/components/schemas/SaveEmailTemplateRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Email template saved; the body holds every culture of the template.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of an email template, returned by get/create/save endpoints.",
                  "$ref": "#/components/schemas/EmailTemplateDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of an email template, returned by get/create/save endpoints.",
                  "$ref": "#/components/schemas/EmailTemplateDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of an email template, returned by get/create/save endpoints.",
                  "$ref": "#/components/schemas/EmailTemplateDefinition"
                }
              }
            }
          },
          "400": {
            "description": "A culture is invalid, no culture was provided, or a culture has a subject without a body or a body without a subject.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.emailTemplate:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Email template not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.emailTemplate:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/enrolmentForms": {
      "get": {
        "tags": [
          "EnrolmentForms"
        ],
        "summary": "List enrolment forms for the tenant",
        "description": "Returns every `customerRegistration` layout of the tenant, ordered by name, with enough of each\nform to render a list without reading them one by one.\n            \nA form whose YAML cannot be parsed is left out; reading it by name still reports it.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Enrolment forms returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Enrolment form returned by the list endpoint.",
                    "$ref": "#/components/schemas/EnrolmentFormListItem"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Enrolment form returned by the list endpoint.",
                    "$ref": "#/components/schemas/EnrolmentFormListItem"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Enrolment form returned by the list endpoint.",
                    "$ref": "#/components/schemas/EnrolmentFormListItem"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.enrolment:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.enrolment:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "EnrolmentForms"
        ],
        "summary": "Create an enrolment form",
        "description": "Creates a new enrolment form.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Name and content of the new form, as typed fields or as `yaml`.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to create an enrolment form.",
                "$ref": "#/components/schemas/CreateEnrolmentFormRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to create an enrolment form.",
                "$ref": "#/components/schemas/CreateEnrolmentFormRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to create an enrolment form.",
                "$ref": "#/components/schemas/CreateEnrolmentFormRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "201": {
            "description": "Enrolment form created.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of an enrolment form, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/EnrolmentFormDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of an enrolment form, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/EnrolmentFormDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of an enrolment form, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/EnrolmentFormDefinition"
                }
              }
            }
          },
          "400": {
            "description": "Name, flow or the resulting configuration is invalid.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.enrolment:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "A form with this name already exists.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.enrolment:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/enrolmentForms/{name}": {
      "delete": {
        "tags": [
          "EnrolmentForms"
        ],
        "summary": "Delete an enrolment form",
        "description": "Removes the enrolment form. Its public URL `/{tenantId}/{name}` then returns 404, including for\nlinks already distributed (QR codes, campaigns, short links); creating a form with the same name\nrestores it. Confirm with the user, naming the form, before calling this.\n            \nA form that another layout uses as its `errorLayoutName` cannot be deleted.\n            \nLocale resource directories are kept, since other forms can use them.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Name of the form: 1 to 100 letters, digits, underscores, hyphens, dots or spaces.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Enrolment form deleted. Its public URL now returns 404."
          },
          "400": {
            "description": "Name is invalid.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.enrolment:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Enrolment form not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The form is used as an error layout by another layout, or the YAML of the form or of another layout cannot be parsed.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.enrolment:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "EnrolmentForms"
        ],
        "summary": "Get an enrolment form",
        "description": "Returns the typed properties of the form together with its YAML, exactly as saved, in `yaml`, so\na caller can render a form editor and a YAML editor from one request.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Name of the form: 1 to 100 letters, digits, underscores, hyphens, dots or spaces.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Enrolment form returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of an enrolment form, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/EnrolmentFormDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of an enrolment form, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/EnrolmentFormDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of an enrolment form, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/EnrolmentFormDefinition"
                }
              }
            }
          },
          "400": {
            "description": "Name is invalid.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.enrolment:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No layout with this name, or the layout is not a `customerRegistration`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The form's YAML cannot be parsed.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.enrolment:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "EnrolmentForms"
        ],
        "summary": "Save an enrolment form",
        "description": "Replaces the form identified by name. The name in the route is authoritative and\nthe form cannot be renamed.\n            \nA form whose YAML no longer parses can only be saved through `yaml`, which replaces the whole\nform.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Name of the form: 1 to 100 letters, digits, underscores, hyphens, dots or spaces.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "New content, as typed fields or as `yaml`.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to save an existing enrolment form.",
                "$ref": "#/components/schemas/SaveEnrolmentFormRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to save an existing enrolment form.",
                "$ref": "#/components/schemas/SaveEnrolmentFormRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to save an existing enrolment form.",
                "$ref": "#/components/schemas/SaveEnrolmentFormRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Enrolment form saved.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of an enrolment form, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/EnrolmentFormDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of an enrolment form, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/EnrolmentFormDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of an enrolment form, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/EnrolmentFormDefinition"
                }
              }
            }
          },
          "400": {
            "description": "Name, flow or the resulting configuration is invalid.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.enrolment:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No layout with this name, or the layout is not a `customerRegistration`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The form's YAML cannot be parsed and the request does not replace it entirely.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.enrolment:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/enrolmentForms/locales": {
      "get": {
        "tags": [
          "EnrolmentLocales"
        ],
        "summary": "List enrolment locale resource directories",
        "description": "Returns every `locales/`-rooted resource directory referenced by an enrolment form's\n`internationalization.resources`, together with the forms that reference it and the cultures it\nalready has translations for.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Resource directories returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Resource directory returned by the list endpoint.",
                    "$ref": "#/components/schemas/EnrolmentLocaleResourceListItem"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Resource directory returned by the list endpoint.",
                    "$ref": "#/components/schemas/EnrolmentLocaleResourceListItem"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Resource directory returned by the list endpoint.",
                    "$ref": "#/components/schemas/EnrolmentLocaleResourceListItem"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.enrolmentFormLocale:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.enrolmentFormLocale:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/enrolmentForms/locales/{culture}/{resourceDir}": {
      "get": {
        "tags": [
          "EnrolmentLocales"
        ],
        "summary": "Get an enrolment locale resource file",
        "parameters": [
          {
            "name": "culture",
            "in": "path",
            "description": "Culture code, e.g. `en`: 1 to 10 letters, digits, hyphens or underscores.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "resourceDir",
            "in": "path",
            "description": "Directory name under `locales/`, e.g. `fields`: 1 to 100 letters, digits, underscores, hyphens, dots or spaces.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Resource file returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "One culture's stored content, returned by the get and built by the save endpoint.",
                  "$ref": "#/components/schemas/EnrolmentLocaleResourceCulture"
                }
              },
              "application/json": {
                "schema": {
                  "description": "One culture's stored content, returned by the get and built by the save endpoint.",
                  "$ref": "#/components/schemas/EnrolmentLocaleResourceCulture"
                }
              },
              "text/json": {
                "schema": {
                  "description": "One culture's stored content, returned by the get and built by the save endpoint.",
                  "$ref": "#/components/schemas/EnrolmentLocaleResourceCulture"
                }
              }
            }
          },
          "400": {
            "description": "Resource or culture is invalid.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.enrolmentFormLocale:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No translations saved for this resource and culture.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The saved translations cannot be parsed.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.enrolmentFormLocale:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "EnrolmentLocales"
        ],
        "summary": "Save an enrolment locale resource file",
        "description": "Merges the request into the culture's stored tree: only the keys present in the request are touched,\nand every key already stored elsewhere in the tree is preserved. A key set to `null`, or to a\nblank string, is removed. An empty object leaves the tree exactly as it is saved.\nThe culture is created when it has no translations yet.",
        "parameters": [
          {
            "name": "culture",
            "in": "path",
            "description": "Culture code, e.g. `en`: 1 to 10 letters, digits, hyphens or underscores.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "resourceDir",
            "in": "path",
            "description": "Directory name under `locales/`, e.g. `fields`: 1 to 100 letters, digits, underscores, hyphens, dots or spaces.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "JSON object of translated strings, optionally nested; every leaf is a string or `null`.",
          "content": {
            "application/json": {
              "schema": { }
            },
            "text/json": {
              "schema": { }
            },
            "application/*+json": {
              "schema": { }
            }
          }
        },
        "responses": {
          "204": {
            "description": "Resource file saved."
          },
          "400": {
            "description": "Resource, culture or the request body is invalid.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.enrolmentFormLocale:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The saved translations cannot be parsed, so the request cannot be merged into them.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.enrolmentFormLocale:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/actito": {
      "get": {
        "tags": [
          "Actito"
        ],
        "summary": "Get the Actito configuration",
        "description": "Returns the current Actito configuration for this tenant.\nThe API key is never returned; the response contains `hasApiKey` instead.\nReturns 404 when Actito is not configured.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Configuration returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The tenant's Actito connection, without the API key.",
                  "$ref": "#/components/schemas/ActitoConfigurationResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The tenant's Actito connection, without the API key.",
                  "$ref": "#/components/schemas/ActitoConfigurationResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The tenant's Actito connection, without the API key.",
                  "$ref": "#/components/schemas/ActitoConfigurationResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.actito.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Actito is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.actito.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Actito"
        ],
        "summary": "Set Actito configuration",
        "description": "Creates or replaces the Actito configuration.\nOmit `apiKey` to keep the saved API key.\nReturns 400 if the API key is missing and none was saved before.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "description": "Connection to the tenant's Actito entity, and how an Actito profile is matched to the holder's passes.",
                "$ref": "#/components/schemas/SetActitoRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Connection to the tenant's Actito entity, and how an Actito profile is matched to the holder's passes.",
                "$ref": "#/components/schemas/SetActitoRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Connection to the tenant's Actito entity, and how an Actito profile is matched to the holder's passes.",
                "$ref": "#/components/schemas/SetActitoRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Configuration saved."
          },
          "400": {
            "description": "Request body is invalid or an API key is required but missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.actito.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.actito.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/actito/scripts": {
      "get": {
        "tags": [
          "ActitoScripts"
        ],
        "summary": "Get the Actito scripts",
        "description": "Returns every script slot; a slot without a script has a null `content`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Scripts returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The scripts the Actito integration can be customised with.",
                  "$ref": "#/components/schemas/ActitoScriptsDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The scripts the Actito integration can be customised with.",
                  "$ref": "#/components/schemas/ActitoScriptsDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The scripts the Actito integration can be customised with.",
                  "$ref": "#/components/schemas/ActitoScriptsDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.actito.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.actito.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "ActitoScripts"
        ],
        "summary": "Set the Actito scripts",
        "description": "A slot left out is untouched, `{ \"content\": \"…\" }` sets the script verbatim and\n`{ \"content\": null }` removes it. An empty content in any slot refuses the whole request; nothing\nis saved.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "description": "Changes to the Actito scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetActitoScriptsRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Changes to the Actito scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetActitoScriptsRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Changes to the Actito scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetActitoScriptsRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Scripts saved."
          },
          "400": {
            "description": "A slot carries an empty content.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.actito.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.actito.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/aparte": {
      "delete": {
        "tags": [
          "Aparte"
        ],
        "summary": "Delete Aparte configuration",
        "description": "Removes the Aparte configuration and its API key. The Aparte scripts are kept. Succeeds even when nothing\nis configured.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Configuration deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.aparte.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.aparte.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Aparte"
        ],
        "summary": "Get the Aparte configuration",
        "description": "Returns the Aparte configuration of the tenant and whether an API key is stored. The API key itself is\nnever returned.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Configuration returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The stored Aparte configuration of the tenant, without its API key.",
                  "$ref": "#/components/schemas/AparteConfigurationResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The stored Aparte configuration of the tenant, without its API key.",
                  "$ref": "#/components/schemas/AparteConfigurationResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The stored Aparte configuration of the tenant, without its API key.",
                  "$ref": "#/components/schemas/AparteConfigurationResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.aparte.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Aparte is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.aparte.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Aparte"
        ],
        "summary": "Set Aparte configuration",
        "description": "Tests the base URL, tenant and API key against the Aparte WalletCrew API, then saves the configuration.\nAparte must answer the test within 10 seconds. Omit `apiKey` to keep the stored key (it is the one\ntested), and `rateLimit` to keep the current settings. Nothing is saved when the request is refused.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The configuration to store.",
          "content": {
            "application/json": {
              "schema": {
                "description": "The Aparte configuration of the tenant, as sent on a save. Every field but `apiKey` and\n`rateLimit` is written as sent, so an omitted `invalidPassType` clears the stored one.",
                "$ref": "#/components/schemas/SetAparteRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "The Aparte configuration of the tenant, as sent on a save. Every field but `apiKey` and\n`rateLimit` is written as sent, so an omitted `invalidPassType` clears the stored one.",
                "$ref": "#/components/schemas/SetAparteRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "The Aparte configuration of the tenant, as sent on a save. Every field but `apiKey` and\n`rateLimit` is written as sent, so an omitted `invalidPassType` clears the stored one.",
                "$ref": "#/components/schemas/SetAparteRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Configuration saved."
          },
          "400": {
            "description": "The body is invalid; `apiKey` is omitted while none is stored; `timeZoneId` is unknown; `baseUrl` is not absolute http(s); `tenant` or `apiKey` cannot be sent as a header; or Aparte refused the credentials.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.aparte.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "502": {
            "description": "The Aparte API could not be reached, did not answer within 10 seconds, or failed while testing the credentials; retry later."
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.aparte.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/aparte/scripts": {
      "get": {
        "tags": [
          "AparteScripts"
        ],
        "summary": "Get the Aparte scripts",
        "description": "Returns every script slot, whether or not the tenant has set it: a slot with no script has a\nnull `content`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Scripts returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The scripts the Aparte integration can be customised with.",
                  "$ref": "#/components/schemas/AparteScriptsDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The scripts the Aparte integration can be customised with.",
                  "$ref": "#/components/schemas/AparteScriptsDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The scripts the Aparte integration can be customised with.",
                  "$ref": "#/components/schemas/AparteScriptsDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.aparte.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.aparte.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "AparteScripts"
        ],
        "summary": "Set the Aparte scripts",
        "description": "Applies every slot the request carries, or none: a slot left out is untouched, `{ \"content\": \"…\" }`\nsets the script, `{ \"content\": null }` deletes it, and an empty content is refused. Leading and\ntrailing whitespace of the content is trimmed.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The slots to change; a slot left out is untouched.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Changes to the Aparte scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetAparteScriptsRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Changes to the Aparte scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetAparteScriptsRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Changes to the Aparte scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetAparteScriptsRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Scripts saved."
          },
          "400": {
            "description": "The body is missing, or a slot carries an empty or whitespace-only content; nothing is written.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.aparte.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.aparte.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/bloomreach": {
      "delete": {
        "tags": [
          "Bloomreach"
        ],
        "summary": "Delete Bloomreach configuration",
        "description": "Removes the Bloomreach configuration and its API key secret. The Bloomreach scripts are kept.\nThis operation is idempotent: it succeeds even when the configuration or the secret is already absent.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Configuration deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.bloomreach.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.bloomreach.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Bloomreach"
        ],
        "summary": "Get the Bloomreach configuration",
        "description": "Returns the non-secret Bloomreach configuration for this tenant and whether an API key secret is currently stored.\nReturns 404 when Bloomreach is not configured.\nThe API key secret itself is never returned.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Configuration returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The tenant's Bloomreach connection, without the API key secret.",
                  "$ref": "#/components/schemas/BloomreachConfigurationResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The tenant's Bloomreach connection, without the API key secret.",
                  "$ref": "#/components/schemas/BloomreachConfigurationResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The tenant's Bloomreach connection, without the API key secret.",
                  "$ref": "#/components/schemas/BloomreachConfigurationResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.bloomreach.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Bloomreach is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The saved configuration is invalid; fix it in the configuration editor.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.bloomreach.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Bloomreach"
        ],
        "summary": "Set Bloomreach configuration",
        "description": "Checks the credentials against Bloomreach, then saves the configuration; nothing is saved when the check\nfails.\nOmit `apiKeySecret` to update settings without rotating the secret.\nWhen `cache` is omitted, the stored cache settings are kept; send it without a duration to disable caching.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "description": "Connection to the tenant's Bloomreach project, and how long customers read from it are reused.",
                "$ref": "#/components/schemas/SetBloomreachRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Connection to the tenant's Bloomreach project, and how long customers read from it are reused.",
                "$ref": "#/components/schemas/SetBloomreachRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Connection to the tenant's Bloomreach project, and how long customers read from it are reused.",
                "$ref": "#/components/schemas/SetBloomreachRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Configuration saved."
          },
          "400": {
            "description": "Request body is invalid, `baseUrl` is not an absolute http or https URL, no secret is sent and none is stored, or Bloomreach answered the credential check with a 4xx (problem type \"Credentials rejected\").",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.bloomreach.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "502": {
            "description": "Bloomreach answered the credential check with a 5xx, or could not be reached."
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.bloomreach.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/bloomreach/scripts": {
      "get": {
        "tags": [
          "BloomreachScripts"
        ],
        "summary": "Get the Bloomreach scripts",
        "description": "Returns every script slot; a slot without a script has a null `content`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Scripts returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The scripts the Bloomreach integration can be customised with.",
                  "$ref": "#/components/schemas/BloomreachScriptsDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The scripts the Bloomreach integration can be customised with.",
                  "$ref": "#/components/schemas/BloomreachScriptsDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The scripts the Bloomreach integration can be customised with.",
                  "$ref": "#/components/schemas/BloomreachScriptsDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.bloomreach.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.bloomreach.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "BloomreachScripts"
        ],
        "summary": "Set the Bloomreach scripts",
        "description": "A slot left out is untouched, `{ \"content\": \"…\" }` sets the script verbatim and\n`{ \"content\": null }` removes it. An empty content in any slot refuses the whole request; nothing\nis saved.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "description": "Changes to the Bloomreach scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetBloomreachScriptsRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Changes to the Bloomreach scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetBloomreachScriptsRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Changes to the Bloomreach scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetBloomreachScriptsRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Scripts saved."
          },
          "400": {
            "description": "A slot carries an empty content.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.bloomreach.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.bloomreach.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/cegid/y2": {
      "get": {
        "tags": [
          "CegidY2"
        ],
        "summary": "Get the Cegid Y2 configuration",
        "description": "Passwords are never returned; each connection carries `hasPassword`, and its business notification\ncredentials `hasPassword`, so callers can tell whether one is stored.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Configuration returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Response body for the Cegid Y2 configuration.",
                  "$ref": "#/components/schemas/CegidY2ConfigurationResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Response body for the Cegid Y2 configuration.",
                  "$ref": "#/components/schemas/CegidY2ConfigurationResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Response body for the Cegid Y2 configuration.",
                  "$ref": "#/components/schemas/CegidY2ConfigurationResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.y2.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Cegid Y2 is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.y2.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "CegidY2"
        ],
        "summary": "Set the Cegid Y2 configuration",
        "description": "Creates or replaces the Cegid Y2 configuration; `connections` is the complete list.\nPasswords are matched to the stored connections by `name`: omit `password`, or\n`businessNotificationSettings.webServiceCredentials.password`, to keep the one stored for the\nconnection of the same name. Renaming a connection therefore requires its passwords again.\nWhen `updateCustomerOnPassInstallationChange`, `cache` or `rateLimit` is omitted, the stored\nvalue is kept; send `cache` without durations to disable caching.\nSaving registers the Y2 business notification subscription of every connection with\n`listenToBusinessNotification`, which disables any other active subscription on that Y2 database.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The configuration to store.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body for setting the Cegid Y2 configuration.",
                "$ref": "#/components/schemas/SetCegidY2Request"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body for setting the Cegid Y2 configuration.",
                "$ref": "#/components/schemas/SetCegidY2Request"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body for setting the Cegid Y2 configuration.",
                "$ref": "#/components/schemas/SetCegidY2Request"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Configuration saved."
          },
          "400": {
            "description": "The body fails validation, two connections share a name, not exactly one connection\n            is the default, a password is missing and none is stored for that connection name, or a connection with\n            `listenToBusinessNotification` has no business notification credentials.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.y2.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.y2.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/cegid/y2/sandbox": {
      "get": {
        "tags": [
          "Cegid"
        ],
        "summary": "Read a Y2 receipt",
        "description": "Returns a summary of the receipt: `items` (one `{ label, quantity, price }` per line, the price\nbeing the tax-included unit price), `date`, `customerId` (the Y2 customer id),\n`currencyId` and `total` (tax included), amounts as Y2 holds them.",
        "parameters": [
          {
            "name": "key",
            "in": "query",
            "description": "Y2 key of the receipt, as `{stump}-{number}`, e.g. `ST202-1409`. The number is the digits\nafter the last `-`; anything else is refused with 400.",
            "schema": {
              "pattern": "(?<Stump>.*)-(?<Number>\\d+)",
              "type": "string"
            }
          },
          {
            "name": "externalReference",
            "in": "query",
            "description": "External reference of the receipt in Y2; 404 when no receipt has it.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Receipt returned.",
            "content": {
              "text/plain": {
                "schema": { }
              },
              "application/json": {
                "schema": { }
              },
              "text/json": {
                "schema": { }
              }
            }
          },
          "400": {
            "description": "The receipt is not designated by exactly one valid identifier.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The sandbox is not enabled for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Cegid Y2 is not configured for this tenant, or no receipt has the external\n            reference.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/admin/extensions/cegid/y2/sandbox/attachReceiptToCustomer": {
      "post": {
        "tags": [
          "Cegid"
        ],
        "summary": "Attach a Y2 receipt to a customer",
        "description": "Finds the Y2 customer with the email, or creates one, then sets that customer on the receipt in Y2,\nthrough the default Y2 connection. A created customer gets `firstName` and `lastName` from the\nbody; when absent, they are derived from the part of the email before `@`: `jane.doe@…` gives\n`jane` and `doe`, a part without a dot is used for both.",
        "parameters": [
          {
            "name": "key",
            "in": "query",
            "description": "Y2 key of the receipt, as `{stump}-{number}`, e.g. `ST202-1409`. The number is the digits\nafter the last `-`; anything else is refused with 400.",
            "schema": {
              "pattern": "(?<Stump>.*)-(?<Number>\\d+)",
              "type": "string"
            }
          },
          {
            "name": "externalReference",
            "in": "query",
            "description": "External reference of the receipt in Y2; 404 when no receipt has it.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "JSON object with `email` (required string), and optional `firstName` and\n            `lastName` strings, used only when the customer is created.",
          "content": {
            "application/json": {
              "schema": { }
            },
            "text/json": {
              "schema": { }
            },
            "application/*+json": {
              "schema": { }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Customer found or created and attached to the receipt.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "string"
                }
              },
              "application/json": {
                "schema": {
                  "type": "string"
                }
              },
              "text/json": {
                "schema": {
                  "type": "string"
                }
              }
            }
          },
          "400": {
            "description": "The receipt is not designated by exactly one valid identifier, or the body has no\n            `email` string, or a `firstName` or `lastName` that is not a string.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the `tenant.y2.listener:write` scope, or the sandbox is not enabled for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Cegid Y2 is not configured for this tenant, or no receipt has the external\n            reference.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "502": {
            "description": "Cegid Y2 refused to attach the customer to the receipt."
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.y2.listener:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/cegid/y2/scripts": {
      "get": {
        "tags": [
          "CegidY2Scripts"
        ],
        "summary": "Get the Cegid Y2 scripts",
        "description": "Returns every script slot, whether or not it is set: an unset slot has a null `content`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Scripts returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The scripts the Cegid Y2 integration can be customised with.",
                  "$ref": "#/components/schemas/CegidY2ScriptsDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The scripts the Cegid Y2 integration can be customised with.",
                  "$ref": "#/components/schemas/CegidY2ScriptsDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The scripts the Cegid Y2 integration can be customised with.",
                  "$ref": "#/components/schemas/CegidY2ScriptsDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.y2.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.y2.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "CegidY2Scripts"
        ],
        "summary": "Set the Cegid Y2 scripts",
        "description": "Applies every slot the request carries, or none: a slot left out is untouched, `{ \"content\": \"…\" }`\nstores the script as sent, `{ \"content\": null }` removes it, and an empty content is refused.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The slot changes to apply.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Changes to the Cegid Y2 scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetCegidY2ScriptsRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Changes to the Cegid Y2 scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetCegidY2ScriptsRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Changes to the Cegid Y2 scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetCegidY2ScriptsRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Scripts saved."
          },
          "400": {
            "description": "A slot carries an empty content.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.y2.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.y2.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/cegid/y2/settings/civilities": {
      "get": {
        "tags": [
          "Cegid"
        ],
        "summary": "List Cegid civilities (titles)",
        "description": "The civilities defined in Y2, as Y2 returns them. A customer's `title` is sent to Y2 as a civility\n`id`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Civilities returned."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.y2.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Cegid Y2 is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.y2.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/cegid/y2/settings/countries": {
      "get": {
        "tags": [
          "Cegid"
        ],
        "summary": "List Cegid countries and regions",
        "description": "One entry per Y2 country, carrying `id`, `languageId`, `shortDescription`,\n`description`, `currencyId`, `nationality`, `isoCode` (`isO3NumCode`,\n`isO2AlphaNumCode`, `isO3AlphaNumCode`; null when Y2 has none) and `regions`, the Y2\nregions whose `countryId` is the country's `id`. A customer's `country` is sent to Y2 as the\nISO alpha-2 code.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Countries and regions returned."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.y2.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Cegid Y2 is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.y2.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/cegid/y2/settings/countries/test": {
      "get": {
        "tags": [
          "Cegid"
        ],
        "summary": "Verify country ISO code uniqueness",
        "description": "Finds the ISO alpha-2 codes shared by several Y2 countries. Customers' countries are sent to Y2 as ISO\nalpha-2 codes, so such a code is ambiguous for Y2. Only the alpha-2 code is checked; countries without one\nare left out.\n            \nThe body is `{ \"duplicatedCountries\": { \"simpleData\": [...], \"fullData\": [...] } }`:\n`simpleData` holds one `{ iso2, values: [{ id, shortDescription }] }` per shared code, and\n`fullData` one array of complete Y2 countries per shared code, in the same order. Both are empty when\nevery code is unique.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Report returned, possibly empty."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.y2.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Cegid Y2 is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.y2.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/cegid/y2/settings/languages": {
      "get": {
        "tags": [
          "Cegid"
        ],
        "summary": "List Cegid supported languages",
        "description": "The languages defined in Y2, as Y2 returns them.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Languages returned."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.y2.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Cegid Y2 is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.y2.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/cegid/y2/stores": {
      "get": {
        "tags": [
          "Cegid"
        ],
        "summary": "List all Cegid Y2 stores",
        "description": "Returns every Y2 store as Y2 sends it, unpaged and unfiltered.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Stores returned."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.y2.store:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Cegid Y2 is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.y2.store:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/cloudflare/turnstile": {
      "delete": {
        "tags": [
          "Turnstile"
        ],
        "summary": "Delete Cloudflare Turnstile configuration",
        "description": "Removes the Turnstile configuration.\nThis disables Turnstile for the tenant.\nAlso removes the Turnstile secret when present.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Configuration deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.cloudflare.turnstile.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.cloudflare.turnstile.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Turnstile"
        ],
        "summary": "Get the Cloudflare Turnstile site key",
        "description": "Returns the public Turnstile site key configured for this tenant.\nReturns 404 when Turnstile is not configured.\nThe secret key is never returned.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Configuration returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The tenant's Cloudflare Turnstile settings, without the secret key.",
                  "$ref": "#/components/schemas/TurnstileConfigurationResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The tenant's Cloudflare Turnstile settings, without the secret key.",
                  "$ref": "#/components/schemas/TurnstileConfigurationResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The tenant's Cloudflare Turnstile settings, without the secret key.",
                  "$ref": "#/components/schemas/TurnstileConfigurationResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.cloudflare.turnstile.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Turnstile is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.cloudflare.turnstile.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Turnstile"
        ],
        "summary": "Set Cloudflare Turnstile configuration",
        "description": "Replaces the site key and proof cookie duration, and the secret key when one is sent.\nOmit `secretKey` to update the site key without rotating the secret.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "description": "Cloudflare Turnstile settings. Once a site key is stored, every customer account creation must pass a\nTurnstile challenge.",
                "$ref": "#/components/schemas/SetTurnstileRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Cloudflare Turnstile settings. Once a site key is stored, every customer account creation must pass a\nTurnstile challenge.",
                "$ref": "#/components/schemas/SetTurnstileRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Cloudflare Turnstile settings. Once a site key is stored, every customer account creation must pass a\nTurnstile challenge.",
                "$ref": "#/components/schemas/SetTurnstileRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Configuration saved."
          },
          "400": {
            "description": "Request body is invalid: `siteKey` is missing, `proofCookieValidityDurationSeconds` is missing or negative, or no secret key is sent and none is saved.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.cloudflare.turnstile.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.cloudflare.turnstile.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/comarch": {
      "delete": {
        "tags": [
          "Comarch"
        ],
        "summary": "Delete Comarch configuration",
        "description": "Removes the Comarch configuration with its client secret and Kafka password. The Comarch scripts are kept.\nSucceeds even when nothing is configured.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Configuration deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.comarch.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.comarch.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Comarch"
        ],
        "summary": "Get the Comarch configuration",
        "description": "Returns the Comarch configuration of the tenant. Secrets are never returned; `hasClientSecret` and\n`kafkaConnection.hasPassword` tell whether they are stored.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Configuration returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The stored Comarch configuration of the tenant, without its secrets.",
                  "$ref": "#/components/schemas/ComarchConfigurationResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The stored Comarch configuration of the tenant, without its secrets.",
                  "$ref": "#/components/schemas/ComarchConfigurationResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The stored Comarch configuration of the tenant, without its secrets.",
                  "$ref": "#/components/schemas/ComarchConfigurationResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.comarch.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Comarch is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.comarch.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Comarch"
        ],
        "summary": "Set Comarch configuration",
        "description": "Creates or updates the Comarch configuration.\nOmit `connection.clientSecret` to keep the stored client secret, and, when `kafkaConnection` is\nsent, `kafkaConnection.password` to keep the stored Kafka password. Omitting `kafkaConnection`\nremoves the Kafka settings and keeps the stored password. Omitting `rateLimit` or\n`providers.coupon` keeps the current settings.\nSaving `providers.customer.updateOnPassInstallationChange` off deletes the\n`extensions.comarch.walletInstallationCustomerUpdater` script.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The configuration to store.",
          "content": {
            "application/json": {
              "schema": {
                "description": "The Comarch configuration of the tenant, as sent on a save.",
                "$ref": "#/components/schemas/SetComarchRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "The Comarch configuration of the tenant, as sent on a save.",
                "$ref": "#/components/schemas/SetComarchRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "The Comarch configuration of the tenant, as sent on a save.",
                "$ref": "#/components/schemas/SetComarchRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Configuration saved."
          },
          "400": {
            "description": "The body is invalid (missing required field, value out of range), or a client secret or Kafka password is omitted while none is stored yet.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.comarch.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.comarch.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/comarch/scripts": {
      "get": {
        "tags": [
          "ComarchScripts"
        ],
        "summary": "Get the Comarch scripts",
        "description": "Returns every script slot, whether or not the tenant has set it: a slot with no script has a\nnull `content`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Scripts returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The scripts the Comarch integration can be customised with.",
                  "$ref": "#/components/schemas/ComarchScriptsDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The scripts the Comarch integration can be customised with.",
                  "$ref": "#/components/schemas/ComarchScriptsDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The scripts the Comarch integration can be customised with.",
                  "$ref": "#/components/schemas/ComarchScriptsDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.comarch.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.comarch.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "ComarchScripts"
        ],
        "summary": "Set the Comarch scripts",
        "description": "Applies every slot the request carries, or none: a slot left out is untouched, `{ \"content\": \"…\" }`\nsets the script, `{ \"content\": null }` deletes it, and an empty content is refused. Leading and\ntrailing whitespace of the content is trimmed.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The slots to change; a slot left out is untouched.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Changes to the Comarch scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetComarchScriptsRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Changes to the Comarch scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetComarchScriptsRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Changes to the Comarch scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetComarchScriptsRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Scripts saved."
          },
          "400": {
            "description": "The body is missing, or a slot carries an empty or whitespace-only content; nothing is written.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.comarch.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.comarch.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/klaviyo": {
      "get": {
        "tags": [
          "Klaviyo"
        ],
        "summary": "Get the Klaviyo configuration",
        "description": "Returns the Klaviyo configuration of the tenant. The private API key is never returned;\n`hasPrivateApiKey` tells whether one is stored.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Configuration returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The stored Klaviyo connection of the tenant, without its private API key.",
                  "$ref": "#/components/schemas/KlaviyoConfigurationResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The stored Klaviyo connection of the tenant, without its private API key.",
                  "$ref": "#/components/schemas/KlaviyoConfigurationResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The stored Klaviyo connection of the tenant, without its private API key.",
                  "$ref": "#/components/schemas/KlaviyoConfigurationResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.klaviyo.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Klaviyo is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.klaviyo.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Klaviyo"
        ],
        "summary": "Set Klaviyo configuration",
        "description": "Creates or replaces the Klaviyo configuration. Every field is written as sent: an omitted `listId`\nclears the stored one and an omitted `enableSmsSupport` turns SMS synchronisation off.\nOmit `privateApiKey` to keep the stored private API key.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The configuration to store.",
          "content": {
            "application/json": {
              "schema": {
                "description": "The Klaviyo connection of the tenant. A save replaces the stored configuration as a whole.",
                "$ref": "#/components/schemas/SetKlaviyoRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "The Klaviyo connection of the tenant. A save replaces the stored configuration as a whole.",
                "$ref": "#/components/schemas/SetKlaviyoRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "The Klaviyo connection of the tenant. A save replaces the stored configuration as a whole.",
                "$ref": "#/components/schemas/SetKlaviyoRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Configuration saved."
          },
          "400": {
            "description": "The body or `siteId` is missing, or `privateApiKey` is omitted while no key is stored yet.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.klaviyo.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.klaviyo.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/klaviyo/scripts": {
      "get": {
        "tags": [
          "KlaviyoScripts"
        ],
        "summary": "Get the Klaviyo scripts",
        "description": "Returns every script slot, whether or not the tenant has set it: a slot with no script has a\nnull `content`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Scripts returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The scripts the Klaviyo integration can be customised with.",
                  "$ref": "#/components/schemas/KlaviyoScriptsDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The scripts the Klaviyo integration can be customised with.",
                  "$ref": "#/components/schemas/KlaviyoScriptsDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The scripts the Klaviyo integration can be customised with.",
                  "$ref": "#/components/schemas/KlaviyoScriptsDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.klaviyo.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.klaviyo.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "KlaviyoScripts"
        ],
        "summary": "Set the Klaviyo scripts",
        "description": "Applies every slot the request carries, or none: a slot left out is untouched, `{ \"content\": \"…\" }`\nsets the script, `{ \"content\": null }` deletes it, and an empty content is refused. Leading and\ntrailing whitespace of the content is trimmed.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The slots to change; a slot left out is untouched.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Changes to the Klaviyo scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetKlaviyoScriptsRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Changes to the Klaviyo scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetKlaviyoScriptsRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Changes to the Klaviyo scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetKlaviyoScriptsRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Scripts saved."
          },
          "400": {
            "description": "The body is missing, or a slot carries an empty or whitespace-only content; nothing is written.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.klaviyo.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.klaviyo.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/salesforce/marketingCloud": {
      "get": {
        "tags": [
          "MarketingCloud"
        ],
        "summary": "Get the Salesforce Marketing Cloud configuration",
        "description": "Returns the current Salesforce Marketing Cloud configuration for this tenant.\nThe signing key is never returned; the response contains `hasSigninKey` instead.\nReturns 404 when Salesforce Marketing Cloud is not configured.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Configuration returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The tenant's Salesforce Marketing Cloud settings, without the signing key.",
                  "$ref": "#/components/schemas/MarketingCloudConfigurationResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The tenant's Salesforce Marketing Cloud settings, without the signing key.",
                  "$ref": "#/components/schemas/MarketingCloudConfigurationResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The tenant's Salesforce Marketing Cloud settings, without the signing key.",
                  "$ref": "#/components/schemas/MarketingCloudConfigurationResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.salesforce.marketingcloud.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Salesforce Marketing Cloud is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.salesforce.marketingcloud.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "MarketingCloud"
        ],
        "summary": "Set the Salesforce Marketing Cloud configuration",
        "description": "Creates or updates the Salesforce Marketing Cloud settings.\nOmit `signinKey` to keep the currently stored signing key.\nReturns 400 when no signing key is provided and none is saved, or when the provided key is shorter\nthan 32 bytes (UTF-8).",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "description": "Salesforce Marketing Cloud settings of the tenant.",
                "$ref": "#/components/schemas/SetMarketingCloudRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Salesforce Marketing Cloud settings of the tenant.",
                "$ref": "#/components/schemas/SetMarketingCloudRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Salesforce Marketing Cloud settings of the tenant.",
                "$ref": "#/components/schemas/SetMarketingCloudRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Configuration saved."
          },
          "400": {
            "description": "Request body is invalid, or the signing key is missing or too short.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.salesforce.marketingcloud.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.salesforce.marketingcloud.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/secutix": {
      "get": {
        "tags": [
          "Secutix"
        ],
        "summary": "Get the Secutix configuration",
        "description": "Returns the tenant's Secutix configuration. The operator secret is never returned;\n`connection.hasSecret` tells whether one is stored.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Configuration returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The tenant's stored Secutix configuration, without the operator secret.",
                  "$ref": "#/components/schemas/SecutixConfigurationResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The tenant's stored Secutix configuration, without the operator secret.",
                  "$ref": "#/components/schemas/SecutixConfigurationResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The tenant's stored Secutix configuration, without the operator secret.",
                  "$ref": "#/components/schemas/SecutixConfigurationResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.secutix.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Secutix is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.secutix.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Secutix"
        ],
        "summary": "Set Secutix configuration",
        "description": "Replaces the tenant's Secutix configuration. `connection` and `pass` are taken as sent;\nomit `connection.secret`, `connection.partner`, `webhook` or `rateLimit` to keep what is\nstored. A first save without a partner uses `neostore`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The configuration to store.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Secutix configuration to store for the tenant.",
                "$ref": "#/components/schemas/SetSecutixRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Secutix configuration to store for the tenant.",
                "$ref": "#/components/schemas/SetSecutixRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Secutix configuration to store for the tenant.",
                "$ref": "#/components/schemas/SetSecutixRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Configuration saved."
          },
          "400": {
            "description": "A required field is missing, a rate limit value is out of range, or no secret is sent and none is stored.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.secutix.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.secutix.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/secutix/scripts": {
      "get": {
        "tags": [
          "SecutixScripts"
        ],
        "summary": "Get the Secutix scripts",
        "description": "Returns every script slot; a slot without a script has a null `content`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Scripts returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The scripts the Secutix integration can be customised with.",
                  "$ref": "#/components/schemas/SecutixScriptsDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The scripts the Secutix integration can be customised with.",
                  "$ref": "#/components/schemas/SecutixScriptsDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The scripts the Secutix integration can be customised with.",
                  "$ref": "#/components/schemas/SecutixScriptsDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.secutix.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.secutix.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "SecutixScripts"
        ],
        "summary": "Set the Secutix scripts",
        "description": "A slot left out is untouched, `{ \"content\": \"…\" }` sets the script verbatim, `{ \"content\": null }`\nremoves it, and an empty content is refused. When a slot is refused, no script is changed.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The slots to change.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Changes to the Secutix scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetSecutixScriptsRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Changes to the Secutix scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetSecutixScriptsRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Changes to the Secutix scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetSecutixScriptsRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Scripts saved."
          },
          "400": {
            "description": "A slot carries an empty content.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.secutix.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.secutix.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/shopify": {
      "delete": {
        "tags": [
          "Shopify"
        ],
        "summary": "Delete the Shopify configuration",
        "description": "Removes the Shopify configuration, which turns the Shopify integration off. The scripts are kept.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Configuration deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.shopify.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.shopify.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Shopify"
        ],
        "summary": "Get the Shopify configuration",
        "description": "Returns the current Shopify configuration for this tenant.\nThe access token is never returned; the response contains `hasAccessToken` instead.\nReturns 404 when Shopify is not configured.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Configuration returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The tenant's Shopify connection, without the access token.",
                  "$ref": "#/components/schemas/ShopifyConfigurationResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The tenant's Shopify connection, without the access token.",
                  "$ref": "#/components/schemas/ShopifyConfigurationResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The tenant's Shopify connection, without the access token.",
                  "$ref": "#/components/schemas/ShopifyConfigurationResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.shopify.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Shopify is not configured for this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.shopify.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Shopify"
        ],
        "summary": "Set the Shopify configuration",
        "description": "Creates or updates the Shopify settings.\nOmit `accessToken` to keep the saved access token.\nReturns 400 when no access token is provided and none is saved.\nThe store URL and access token are checked against Shopify before anything is saved.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "description": "Connection to the tenant's Shopify store.",
                "$ref": "#/components/schemas/SetShopifyRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Connection to the tenant's Shopify store.",
                "$ref": "#/components/schemas/SetShopifyRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Connection to the tenant's Shopify store.",
                "$ref": "#/components/schemas/SetShopifyRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Configuration saved."
          },
          "400": {
            "description": "Request body is invalid, `shopifyUrl` is neither a store host nor an http or https URL, an access token is required but missing or unusable as a header, or Shopify answered the credential check with a 4xx (problem type \"Credentials rejected\").",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.shopify.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "502": {
            "description": "Shopify answered the credential check with a 5xx, or the store could not be reached."
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.shopify.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/extensions/shopify/scripts": {
      "get": {
        "tags": [
          "ShopifyScripts"
        ],
        "summary": "Get the Shopify scripts",
        "description": "Returns every script slot; a slot without a script has a null `content`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Scripts returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The scripts the Shopify integration can be customised with.",
                  "$ref": "#/components/schemas/ShopifyScriptsDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The scripts the Shopify integration can be customised with.",
                  "$ref": "#/components/schemas/ShopifyScriptsDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The scripts the Shopify integration can be customised with.",
                  "$ref": "#/components/schemas/ShopifyScriptsDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.shopify.settings:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.shopify.settings:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "ShopifyScripts"
        ],
        "summary": "Set the Shopify scripts",
        "description": "A slot left out is untouched, `{ \"content\": \"…\" }` sets the script verbatim and\n`{ \"content\": null }` removes it. An empty content in any slot refuses the whole request; nothing\nis saved.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "description": "Changes to the Shopify scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetShopifyScriptsRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Changes to the Shopify scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetShopifyScriptsRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Changes to the Shopify scripts. A slot left out is left untouched.",
                "$ref": "#/components/schemas/SetShopifyScriptsRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "204": {
            "description": "Scripts saved."
          },
          "400": {
            "description": "A slot carries an empty content.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.shopify.settings:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.shopify.settings:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/flows": {
      "get": {
        "tags": [
          "Flows"
        ],
        "summary": "List flows for the tenant",
        "description": "Returns every flow, ordered by name.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Flows returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Flow returned by the list endpoint.",
                    "$ref": "#/components/schemas/FlowListItem"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Flow returned by the list endpoint.",
                    "$ref": "#/components/schemas/FlowListItem"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Flow returned by the list endpoint.",
                    "$ref": "#/components/schemas/FlowListItem"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.flow:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The tenant's flow configuration cannot be parsed.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.flow:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Flows"
        ],
        "summary": "Create a flow",
        "description": "Adds a new flow. Every step must be of a step type available to the tenant and match that type's\nschema, else 400.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Name, type and steps of the new flow.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to create a flow.",
                "$ref": "#/components/schemas/CreateFlowRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to create a flow.",
                "$ref": "#/components/schemas/CreateFlowRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to create a flow.",
                "$ref": "#/components/schemas/CreateFlowRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "201": {
            "description": "Flow created.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of a flow, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/FlowDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of a flow, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/FlowDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of a flow, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/FlowDefinition"
                }
              }
            }
          },
          "400": {
            "description": "Name, flow type or a step is invalid.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.flow:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "A flow with this name already exists, or the tenant's flow configuration cannot be parsed.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.flow:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/flows/{name}": {
      "delete": {
        "tags": [
          "Flows"
        ],
        "summary": "Delete a flow",
        "description": "Removes the flow. Refused with a conflict while any layout still references the flow by name, or while\na layout cannot be parsed.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Name of the flow, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Flow deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.flow:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Flow not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The flow is still referenced by one or more layouts, a layout cannot be parsed, or the tenant's flow configuration cannot be parsed.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.flow:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Flows"
        ],
        "summary": "Get a flow",
        "description": "Returns the type and the ordered steps of the flow identified by name. Step\nconfiguration is returned exactly as saved, including step types not available to the tenant.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Name of the flow, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Flow returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of a flow, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/FlowDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of a flow, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/FlowDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of a flow, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/FlowDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.flow:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Flow not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The tenant's flow configuration cannot be parsed.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.flow:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Flows"
        ],
        "summary": "Save a flow",
        "description": "Replaces the type and the steps of an existing flow, leaving every other flow untouched.\nThe flow cannot be renamed: the name in the route is authoritative.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Name of the flow, case-sensitive.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "New type and steps of the flow.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to save an existing flow.",
                "$ref": "#/components/schemas/SaveFlowRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to save an existing flow.",
                "$ref": "#/components/schemas/SaveFlowRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to save an existing flow.",
                "$ref": "#/components/schemas/SaveFlowRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Flow saved.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of a flow, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/FlowDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of a flow, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/FlowDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of a flow, returned by the get/create/save endpoints.",
                  "$ref": "#/components/schemas/FlowDefinition"
                }
              }
            }
          },
          "400": {
            "description": "Flow type or a step is invalid.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.flow:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Flow not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The tenant's flow configuration cannot be parsed.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.flow:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/media/images": {
      "get": {
        "tags": [
          "Media"
        ],
        "summary": "List public media images for the tenant",
        "description": "Returns every public image, ordered by file name. Other public files are left out.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Media images returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A public media image.",
                    "$ref": "#/components/schemas/MediaImageDefinition"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A public media image.",
                    "$ref": "#/components/schemas/MediaImageDefinition"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A public media image.",
                    "$ref": "#/components/schemas/MediaImageDefinition"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.media:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.media:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Media"
        ],
        "summary": "Upload a public media image",
        "description": "Saves the uploaded image under the file's own name, replacing any image with the same name.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "multipart/form-data": {
              "schema": {
                "type": "object",
                "properties": {
                  "file": {
                    "type": "string",
                    "description": "Image file to upload (multipart/form-data). The request is limited to 8 MB.",
                    "format": "binary"
                  }
                }
              },
              "encoding": {
                "file": {
                  "style": "form"
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Media image uploaded.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A public media image.",
                  "$ref": "#/components/schemas/MediaImageDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A public media image.",
                  "$ref": "#/components/schemas/MediaImageDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A public media image.",
                  "$ref": "#/components/schemas/MediaImageDefinition"
                }
              }
            }
          },
          "400": {
            "description": "No file or an empty file was sent, or its name breaks the naming rule.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.media:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "413": {
            "description": "The request body is larger than 8 MB.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.media:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/media/images/{fileName}": {
      "delete": {
        "tags": [
          "Media"
        ],
        "summary": "Delete a public media image",
        "description": "Removes the image. Its URL starts returning 404, including where a page, an e-mail or a pass still uses\nit.",
        "parameters": [
          {
            "name": "fileName",
            "in": "path",
            "description": "File name as returned in `fileName`.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Media image deleted."
          },
          "400": {
            "description": "The file name breaks the naming rule.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.media:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Media image not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.media:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/passTypes": {
      "get": {
        "tags": [
          "PassTypes"
        ],
        "summary": "List every pass template of the tenant.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Templates returned, in name order.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A pass template as it appears in the list.",
                    "$ref": "#/components/schemas/PassTypeListItem"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A pass template as it appears in the list.",
                    "$ref": "#/components/schemas/PassTypeListItem"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A pass template as it appears in the list.",
                    "$ref": "#/components/schemas/PassTypeListItem"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.passType:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.passType:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/passTypes/{name}": {
      "delete": {
        "tags": [
          "PassTypes"
        ],
        "summary": "Delete a pass template, its translations and its images.",
        "description": "Refused while any pass is still issued from the template.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Template name, the `passType` its passes carry.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Template deleted, with its translations and images."
          },
          "400": {
            "description": "The name is not valid: 1 to 100 letters, digits, underscores, hyphens, dots or spaces.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.passType:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No such template.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "Passes are still issued from the template (type `#pass-template-in-use`).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.passType:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "PassTypes"
        ],
        "summary": "Retrieve one pass template, wording included.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Template name, the `passType` its passes carry.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Template returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "One pass template in full.",
                  "$ref": "#/components/schemas/PassTypeDetail"
                }
              },
              "application/json": {
                "schema": {
                  "description": "One pass template in full.",
                  "$ref": "#/components/schemas/PassTypeDetail"
                }
              },
              "text/json": {
                "schema": {
                  "description": "One pass template in full.",
                  "$ref": "#/components/schemas/PassTypeDetail"
                }
              }
            }
          },
          "400": {
            "description": "The name is not valid: 1 to 100 letters, digits, underscores, hyphens, dots or spaces.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.passType:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No such template.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The stored template cannot be read (type `#unreadable-configuration-file`); repair it in the Advanced Configuration editor.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.passType:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "PassTypes"
        ],
        "summary": "Create or replace a pass template.",
        "description": "The name in the route is the template's identity: the caller chooses it, and the template is created\nwhen none exists under the name. Repeating the same request leaves the same template behind, so a\nretry after a lost response is safe.\n            \nSend the configuration whole: this replaces the stored template rather than merging into it, so\nanything left out is removed, and wording left out is deleted in every language.\n`kind` is fixed at creation and cannot be changed afterwards.\n            \n`If-None-Match: *` restricts the request to creating: a template already stored under the name\nis refused rather than replaced. Without it a caller that needs to know whether it created or\nreplaced reads the status code.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Template name, the `passType` its passes carry. A new name is 2 to 100 letters, digits, underscores,\nspaces or hyphens, starting and ending with a letter, digit or underscore; an existing template may keep\na name with dots.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Template payload.",
          "content": {
            "application/json": {
              "schema": {
                "description": "A pass template to create or replace.",
                "$ref": "#/components/schemas/SavePassTypeRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "A pass template to create or replace.",
                "$ref": "#/components/schemas/SavePassTypeRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "A pass template to create or replace.",
                "$ref": "#/components/schemas/SavePassTypeRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Template replaced.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "One pass template in full.",
                  "$ref": "#/components/schemas/PassTypeDetail"
                }
              },
              "application/json": {
                "schema": {
                  "description": "One pass template in full.",
                  "$ref": "#/components/schemas/PassTypeDetail"
                }
              },
              "text/json": {
                "schema": {
                  "description": "One pass template in full.",
                  "$ref": "#/components/schemas/PassTypeDetail"
                }
              }
            }
          },
          "201": {
            "description": "Template created.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "One pass template in full.",
                  "$ref": "#/components/schemas/PassTypeDetail"
                }
              },
              "application/json": {
                "schema": {
                  "description": "One pass template in full.",
                  "$ref": "#/components/schemas/PassTypeDetail"
                }
              },
              "text/json": {
                "schema": {
                  "description": "One pass template in full.",
                  "$ref": "#/components/schemas/PassTypeDetail"
                }
              }
            }
          },
          "400": {
            "description": "The name is not usable, the payload is invalid or incomplete for its kind, it carries wording in a\nlanguage code that is not 1 to 10 letters, digits or hyphens, or it changes `kind`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.passType:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The stored template cannot be read (type `#unreadable-configuration-file`); repair it before replacing it.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "412": {
            "description": "A template of that name exists and the request asked to create only (type `#name-already-taken`).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.passType:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/passTypes/{name}/images": {
      "get": {
        "tags": [
          "PassTypeImages"
        ],
        "summary": "List the images stored for a pass template.",
        "description": "Lists every image the template carries; a caller copying or exporting a template reads the set from\nhere rather than from the paths the configuration mentions.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Template name, the `passType` its passes carry.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Images returned, in file name order. Empty when the template carries none.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A template image.",
                    "$ref": "#/components/schemas/PassTypeImageInfo"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A template image.",
                    "$ref": "#/components/schemas/PassTypeImageInfo"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A template image.",
                    "$ref": "#/components/schemas/PassTypeImageInfo"
                  }
                }
              }
            }
          },
          "400": {
            "description": "The name is not valid: 1 to 100 letters, digits, underscores, hyphens, dots or spaces.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.passType:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No such template.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.passType:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/passTypes/{name}/images/{imageName}": {
      "delete": {
        "tags": [
          "PassTypeImages"
        ],
        "summary": "Delete a template image.",
        "description": "The image is deleted even when the template still refers to it.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Template name, the `passType` its passes carry.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "imageName",
            "in": "path",
            "description": "Image file name, as listed by `GET {name}/images`.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Image deleted."
          },
          "400": {
            "description": "The template or image name is not usable.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.passType:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No such image. A missing template also answers 404.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.passType:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "PassTypeImages"
        ],
        "summary": "Retrieve the bytes of a template image.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Template name, the `passType` its passes carry.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "imageName",
            "in": "path",
            "description": "Image file name, as listed by `GET {name}/images`.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Image bytes, with the content type of the file extension."
          },
          "400": {
            "description": "The template or image name is not usable.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.passType:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No such image. A missing template also answers 404.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.passType:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "PassTypeImages"
        ],
        "summary": "Upload or replace an image of a pass template.",
        "description": "Uploading the same file name again replaces it, and the image keeps the same path. The image may be\nrecompressed. No pass is pushed to devices by this call.",
        "parameters": [
          {
            "name": "name",
            "in": "path",
            "description": "Template name, the `passType` its passes carry.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "imageName",
            "in": "path",
            "description": "Image file name, e.g. `apple-strip.png`: starts with a letter or digit, then letters, digits,\nunderscores or hyphens, and one `.png`, `.jpg`, `.jpeg`, `.gif` or `.webp` extension.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "multipart/form-data": {
              "schema": {
                "type": "object",
                "properties": {
                  "file": {
                    "type": "string",
                    "description": "Image file (multipart/form-data). PNG, JPEG, GIF or WebP, matching the extension of `imageName`; the whole request is capped at 8 MB.",
                    "format": "binary"
                  }
                }
              },
              "encoding": {
                "file": {
                  "style": "form"
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Image stored; returns its path.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A template image.",
                  "$ref": "#/components/schemas/PassTypeImageInfo"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A template image.",
                  "$ref": "#/components/schemas/PassTypeImageInfo"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A template image.",
                  "$ref": "#/components/schemas/PassTypeImageInfo"
                }
              }
            }
          },
          "400": {
            "description": "The template or image name is not usable, the file is missing or empty, or its content is not a supported\nimage or not the image its extension claims.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.passType:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No such template.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "413": {
            "description": "The request body is larger than 8 MB.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.passType:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/permissions": {
      "get": {
        "tags": [
          "Permissions"
        ],
        "summary": "List available permissions and their descriptions",
        "description": "Returns the areas of the core platform and of the extensions enabled for this tenant; the areas of an\nextension the tenant has not enabled are left out. Ordered by area code.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Permissions returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A group of scopes sharing the same prefix.",
                    "$ref": "#/components/schemas/PermissionAreaWeb"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A group of scopes sharing the same prefix.",
                    "$ref": "#/components/schemas/PermissionAreaWeb"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A group of scopes sharing the same prefix.",
                    "$ref": "#/components/schemas/PermissionAreaWeb"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.access:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.access:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/roles": {
      "get": {
        "tags": [
          "Roles"
        ],
        "summary": "List available roles and permissions for the tenant",
        "description": "Returns every role, ordered by name, with its permissions resolved.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Roles returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A role and the permissions it grants.",
                    "$ref": "#/components/schemas/RoleDefinition"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A role and the permissions it grants.",
                    "$ref": "#/components/schemas/RoleDefinition"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A role and the permissions it grants.",
                    "$ref": "#/components/schemas/RoleDefinition"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.access:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.access:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Roles"
        ],
        "summary": "Create a new role",
        "description": "Adds a new role, which can then be assigned to users.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Name and permissions of the new role.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to create a role.",
                "$ref": "#/components/schemas/CreateRoleRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to create a role.",
                "$ref": "#/components/schemas/CreateRoleRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to create a role.",
                "$ref": "#/components/schemas/CreateRoleRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "201": {
            "description": "Role created.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A role and the permissions it grants.",
                  "$ref": "#/components/schemas/RoleDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A role and the permissions it grants.",
                  "$ref": "#/components/schemas/RoleDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A role and the permissions it grants.",
                  "$ref": "#/components/schemas/RoleDefinition"
                }
              }
            }
          },
          "400": {
            "description": "Name is missing, too long or has a forbidden character, or permissions are missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.access.role:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "A role with this name already exists, or the name is `administrator`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.access.role:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/roles/{roleName}": {
      "delete": {
        "tags": [
          "Roles"
        ],
        "summary": "Delete a role",
        "description": "Removes a role. The `administrator` role cannot be deleted.\n            \nUsers who hold the role no longer get any permission from it.",
        "parameters": [
          {
            "name": "roleName",
            "in": "path",
            "description": "Name of the role, matched case-insensitively.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Role deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.access.role:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Role not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The role is the reserved `administrator` role.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.access.role:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Roles"
        ],
        "summary": "Get a specific role and permissions for the tenant",
        "description": "Returns the role with its permissions resolved.\n            \nAlso available to a caller whose own role on the tenant is `roleName`, even without the\n`tenant.access:read` scope, so any user can read what their own role grants.",
        "parameters": [
          {
            "name": "roleName",
            "in": "path",
            "description": "Name of the role, matched case-insensitively.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Role returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A role and the permissions it grants.",
                  "$ref": "#/components/schemas/RoleDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A role and the permissions it grants.",
                  "$ref": "#/components/schemas/RoleDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A role and the permissions it grants.",
                  "$ref": "#/components/schemas/RoleDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the `tenant.access:read` scope and does not hold this role.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Role not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      },
      "put": {
        "tags": [
          "Roles"
        ],
        "summary": "Update a role's permissions",
        "description": "Replaces the permission list of an existing role.\nThe `administrator` role cannot be modified.",
        "parameters": [
          {
            "name": "roleName",
            "in": "path",
            "description": "Name of the role, matched case-insensitively.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Permissions replacing the current ones.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to update a role's permissions.",
                "$ref": "#/components/schemas/UpdateRoleRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to update a role's permissions.",
                "$ref": "#/components/schemas/UpdateRoleRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to update a role's permissions.",
                "$ref": "#/components/schemas/UpdateRoleRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Role updated.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A role and the permissions it grants.",
                  "$ref": "#/components/schemas/RoleDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A role and the permissions it grants.",
                  "$ref": "#/components/schemas/RoleDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A role and the permissions it grants.",
                  "$ref": "#/components/schemas/RoleDefinition"
                }
              }
            }
          },
          "400": {
            "description": "Permissions are missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.access.role:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Role not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The role is the reserved `administrator` role.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.access.role:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/security/checkinPolicy": {
      "get": {
        "tags": [
          "Security"
        ],
        "summary": "Get the check-in policy",
        "description": "Returns the `checkInSecurityMode`. A tenant that has not configured one\ngets `full`, the policy applied in that case.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Check-in policy returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Check-in policy currently applied by this tenant.",
                  "$ref": "#/components/schemas/CheckinPolicyDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Check-in policy currently applied by this tenant.",
                  "$ref": "#/components/schemas/CheckinPolicyDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Check-in policy currently applied by this tenant.",
                  "$ref": "#/components/schemas/CheckinPolicyDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.enrolment:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant has no readable security configuration.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.enrolment:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Security"
        ],
        "summary": "Configure the check-in policy",
        "description": "Replaces the `checkInSecurityMode`. Every other security setting, the\ngeneral secrets included, keeps its value. Takes effect on the next registration.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The check-in policy to store.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to configure the check-in policy.",
                "$ref": "#/components/schemas/UpdateCheckinPolicyRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to configure the check-in policy.",
                "$ref": "#/components/schemas/UpdateCheckinPolicyRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to configure the check-in policy.",
                "$ref": "#/components/schemas/UpdateCheckinPolicyRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Check-in policy updated.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Check-in policy currently applied by this tenant.",
                  "$ref": "#/components/schemas/CheckinPolicyDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Check-in policy currently applied by this tenant.",
                  "$ref": "#/components/schemas/CheckinPolicyDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Check-in policy currently applied by this tenant.",
                  "$ref": "#/components/schemas/CheckinPolicyDefinition"
                }
              }
            }
          },
          "400": {
            "description": "The policy is missing or not one of the supported values.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.enrolment:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant has no security configuration, or it cannot be parsed.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.enrolment:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/security/secrets": {
      "get": {
        "tags": [
          "Security"
        ],
        "summary": "Get the general secrets",
        "description": "Returns `secret1` and `secret2` in clear, as integrators need them to sign the values they\nsend.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "General secrets returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "General secrets of the tenant.",
                  "$ref": "#/components/schemas/GeneralSecretsDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "General secrets of the tenant.",
                  "$ref": "#/components/schemas/GeneralSecretsDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "General secrets of the tenant.",
                  "$ref": "#/components/schemas/GeneralSecretsDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.generalSecret:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant has no readable security configuration.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.generalSecret:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Security"
        ],
        "summary": "Configure the general secrets",
        "description": "Replaces `secret1` and `secret2`. Every other security setting,\nthe check-in policy included, keeps its value.\n            \n**Rotating a secret invalidates every link and token already signed with it.** Both values are replaced\non every call, so send back the current value of the one you do not mean to change. To rotate without\na cut-over, move the current `secret1` to `secret2` and set a new `secret1`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Both secrets, replacing the current ones.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to configure the general secrets. Both values are replaced.",
                "$ref": "#/components/schemas/UpdateGeneralSecretsRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to configure the general secrets. Both values are replaced.",
                "$ref": "#/components/schemas/UpdateGeneralSecretsRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to configure the general secrets. Both values are replaced.",
                "$ref": "#/components/schemas/UpdateGeneralSecretsRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "General secrets updated.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "General secrets of the tenant.",
                  "$ref": "#/components/schemas/GeneralSecretsDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "General secrets of the tenant.",
                  "$ref": "#/components/schemas/GeneralSecretsDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "General secrets of the tenant.",
                  "$ref": "#/components/schemas/GeneralSecretsDefinition"
                }
              }
            }
          },
          "400": {
            "description": "One of the secrets is missing or empty.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.generalSecret:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "The tenant has no security configuration, or it cannot be parsed.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.generalSecret:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/sftp/files": {
      "get": {
        "tags": [
          "Sftp"
        ],
        "summary": "List files in a tenant's SFTP inbox",
        "description": "Returns every file currently visible in the tenant's SFTP inbox, each tagged with its status.\nReturns an empty list — not an error — when the tenant has no SFTP inbox.",
        "parameters": [
          {
            "name": "status",
            "in": "query",
            "description": "Optional filter: `pending`, `processed`, or `error`.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "File list returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "One file sitting in the tenant's SFTP inbox.",
                    "$ref": "#/components/schemas/SftpFileResponse"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "One file sitting in the tenant's SFTP inbox.",
                    "$ref": "#/components/schemas/SftpFileResponse"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "One file sitting in the tenant's SFTP inbox.",
                    "$ref": "#/components/schemas/SftpFileResponse"
                  }
                }
              }
            }
          },
          "400": {
            "description": "The status filter is not one of the accepted values.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.sftp:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.sftp:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/sftp/files/content": {
      "get": {
        "tags": [
          "Sftp"
        ],
        "summary": "Download one SFTP-dropped file",
        "description": "Streams the file exactly as the customer dropped it — no parsing, no reformatting — as an\nattachment named after the file itself.\n            \nThe body is gzip-compressed whenever the caller sends `Accept-Encoding: gzip`, which every browser\ndoes. This is transport compression, not a different artifact — the client decompresses\ntransparently and ends up with the original file, byte for byte, under its original name. A caller\nthat does not send it gets the bytes uncompressed.\n            \nRequires `tenant.sftp:download`; `tenant.sftp:read` gives access to file names, row counts and pass\nidentifiers, never to the customer data in the file.",
        "parameters": [
          {
            "name": "blobPath",
            "in": "query",
            "description": "File run identifier, exactly as returned in `blobPath` by the files list endpoint.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "File content returned as an attachment.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "application/json": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "text/json": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              }
            }
          },
          "400": {
            "description": "`blobPath` is missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.sftp:download</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No file with this `blobPath` in the tenant's SFTP inbox. A pending file gets a new `blobPath` once imported: list the files again.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.sftp:download"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/sftp/files/log": {
      "get": {
        "tags": [
          "Sftp"
        ],
        "summary": "Get the import log for one SFTP-dropped file",
        "description": "Returns the full story of what happened when this file was imported: whether the import\nitself ran cleanly, aggregate row counts, and a per-pass breakdown of which customer\npasses were touched and which failed, with the reason.",
        "parameters": [
          {
            "name": "blobPath",
            "in": "query",
            "description": "File run identifier, exactly as returned in `blobPath` by the files list endpoint.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Import log returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full story of what happened when one SFTP-dropped file was imported.",
                  "$ref": "#/components/schemas/SftpImportLogResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full story of what happened when one SFTP-dropped file was imported.",
                  "$ref": "#/components/schemas/SftpImportLogResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full story of what happened when one SFTP-dropped file was imported.",
                  "$ref": "#/components/schemas/SftpImportLogResponse"
                }
              }
            }
          },
          "400": {
            "description": "`blobPath` is missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.sftp:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No file with this `blobPath` in the tenant's SFTP inbox.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.sftp:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/sftp/status": {
      "get": {
        "tags": [
          "Sftp"
        ],
        "summary": "Get SFTP status for a tenant",
        "description": "Reports whether SFTP file import is enabled for the tenant, and a quick activity\nsummary. A tenant with no SFTP inbox simply has the feature disabled — this is the normal\ncase for most tenants, reflected as `sftpEnabled: false`, never a 404.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Status returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Quick-glance SFTP activity summary for a tenant.",
                  "$ref": "#/components/schemas/SftpStatusResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Quick-glance SFTP activity summary for a tenant.",
                  "$ref": "#/components/schemas/SftpStatusResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Quick-glance SFTP activity summary for a tenant.",
                  "$ref": "#/components/schemas/SftpStatusResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.sftp:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.sftp:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/socialSignIn/apple": {
      "delete": {
        "tags": [
          "AppleSignIn"
        ],
        "summary": "Delete sign in with Apple settings",
        "description": "Clears the `serviceIdentifier`, disabling sign in with Apple for\nthe tenant. The Apple Wallet settings are preserved.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Sign in with Apple disabled, or was never configured."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.connector.social:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.connector.social:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "AppleSignIn"
        ],
        "summary": "Get sign in with Apple settings",
        "description": "Returns the sign in with Apple `serviceIdentifier`, empty when Apple Wallet is configured but sign in\nwith Apple is not.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Settings returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Sign in with Apple settings.",
                  "$ref": "#/components/schemas/AppleSignInDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Sign in with Apple settings.",
                  "$ref": "#/components/schemas/AppleSignInDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Sign in with Apple settings.",
                  "$ref": "#/components/schemas/AppleSignInDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.connector.social:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Apple Wallet is not configured for this tenant, so neither is sign in with Apple.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.connector.social:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "AppleSignIn"
        ],
        "summary": "Configure sign in with Apple",
        "description": "Replaces the `serviceIdentifier`, leaving the Apple Wallet settings untouched.\nApple Wallet must already be configured for the tenant.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to configure sign in with Apple.",
                "$ref": "#/components/schemas/UpdateAppleSignInRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to configure sign in with Apple.",
                "$ref": "#/components/schemas/UpdateAppleSignInRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to configure sign in with Apple.",
                "$ref": "#/components/schemas/UpdateAppleSignInRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Settings updated; the body is the stored settings.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Sign in with Apple settings.",
                  "$ref": "#/components/schemas/AppleSignInDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Sign in with Apple settings.",
                  "$ref": "#/components/schemas/AppleSignInDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Sign in with Apple settings.",
                  "$ref": "#/components/schemas/AppleSignInDefinition"
                }
              }
            }
          },
          "400": {
            "description": "`serviceIdentifier` is missing or empty.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.connector.social:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "Apple Wallet is not yet configured for this tenant; configure it first.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.connector.social:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/socialSignIn/facebook": {
      "delete": {
        "tags": [
          "FacebookSignIn"
        ],
        "summary": "Delete sign in with Facebook settings",
        "description": "Removes the Facebook app credentials, disabling sign in with Facebook for the tenant.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Configuration deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.connector.social:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.connector.social:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "FacebookSignIn"
        ],
        "summary": "Get sign in with Facebook settings",
        "description": "Returns the Facebook app ID and whether an app secret is configured.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Settings returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Sign in with Facebook settings, without the app secret.",
                  "$ref": "#/components/schemas/FacebookSignInDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Sign in with Facebook settings, without the app secret.",
                  "$ref": "#/components/schemas/FacebookSignInDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Sign in with Facebook settings, without the app secret.",
                  "$ref": "#/components/schemas/FacebookSignInDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.connector.social:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Sign in with Facebook is not configured.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.connector.social:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "FacebookSignIn"
        ],
        "summary": "Configure sign in with Facebook",
        "description": "Creates or replaces the Facebook app credentials.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to configure sign in with Facebook.",
                "$ref": "#/components/schemas/UpdateFacebookSignInRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to configure sign in with Facebook.",
                "$ref": "#/components/schemas/UpdateFacebookSignInRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to configure sign in with Facebook.",
                "$ref": "#/components/schemas/UpdateFacebookSignInRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Settings updated; the body is the stored settings.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Sign in with Facebook settings, without the app secret.",
                  "$ref": "#/components/schemas/FacebookSignInDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Sign in with Facebook settings, without the app secret.",
                  "$ref": "#/components/schemas/FacebookSignInDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Sign in with Facebook settings, without the app secret.",
                  "$ref": "#/components/schemas/FacebookSignInDefinition"
                }
              }
            }
          },
          "400": {
            "description": "`appId` is missing, or no app secret was supplied and none is currently configured.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.connector.social:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.connector.social:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/socialSignIn/google": {
      "delete": {
        "tags": [
          "GoogleSignIn"
        ],
        "summary": "Delete sign in with Google settings",
        "description": "Clears the sign-in fields (`clientId`, `gtmId`), disabling sign in\nwith Google for the tenant.\n            \nThe Google Wallet issuer configuration, if any, is preserved.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Configuration deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.connector.social:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.connector.social:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "GoogleSignIn"
        ],
        "summary": "Get sign in with Google settings",
        "description": "Returns the Google sign-in fields.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Settings returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Sign in with Google settings.",
                  "$ref": "#/components/schemas/GoogleSignInDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Sign in with Google settings.",
                  "$ref": "#/components/schemas/GoogleSignInDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Sign in with Google settings.",
                  "$ref": "#/components/schemas/GoogleSignInDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.connector.social:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Sign in with Google is not configured.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.connector.social:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "GoogleSignIn"
        ],
        "summary": "Configure sign in with Google",
        "description": "Creates or replaces the Google sign-in fields. The Google Wallet issuer configuration, if any, is preserved.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to configure sign in with Google.",
                "$ref": "#/components/schemas/UpdateGoogleSignInRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to configure sign in with Google.",
                "$ref": "#/components/schemas/UpdateGoogleSignInRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to configure sign in with Google.",
                "$ref": "#/components/schemas/UpdateGoogleSignInRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Settings updated; the body is the stored settings.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Sign in with Google settings.",
                  "$ref": "#/components/schemas/GoogleSignInDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Sign in with Google settings.",
                  "$ref": "#/components/schemas/GoogleSignInDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Sign in with Google settings.",
                  "$ref": "#/components/schemas/GoogleSignInDefinition"
                }
              }
            }
          },
          "400": {
            "description": "`clientId` is missing or empty.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.connector.social:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.connector.social:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/socialSignIn/line": {
      "delete": {
        "tags": [
          "LineSignIn"
        ],
        "summary": "Delete sign in with LINE settings",
        "description": "Removes the LINE Login channel configuration, disabling sign in with LINE for the tenant.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Configuration deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.connector.social:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.connector.social:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "LineSignIn"
        ],
        "summary": "Get sign in with LINE settings",
        "description": "Returns the LINE Login channel configuration.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Settings returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Sign in with LINE settings.",
                  "$ref": "#/components/schemas/LineSignInDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Sign in with LINE settings.",
                  "$ref": "#/components/schemas/LineSignInDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Sign in with LINE settings.",
                  "$ref": "#/components/schemas/LineSignInDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.connector.social:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Sign in with LINE is not configured.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.connector.social:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "LineSignIn"
        ],
        "summary": "Configure sign in with LINE",
        "description": "Creates or replaces the LINE Login channel configuration.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to configure sign in with LINE.",
                "$ref": "#/components/schemas/UpdateLineSignInRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to configure sign in with LINE.",
                "$ref": "#/components/schemas/UpdateLineSignInRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to configure sign in with LINE.",
                "$ref": "#/components/schemas/UpdateLineSignInRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Settings updated; the body is the stored settings.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Sign in with LINE settings.",
                  "$ref": "#/components/schemas/LineSignInDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Sign in with LINE settings.",
                  "$ref": "#/components/schemas/LineSignInDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Sign in with LINE settings.",
                  "$ref": "#/components/schemas/LineSignInDefinition"
                }
              }
            }
          },
          "400": {
            "description": "`clientId` is missing or empty.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.connector.social:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.connector.social:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/stores": {
      "get": {
        "tags": [
          "Stores"
        ],
        "summary": "List stores for the tenant",
        "description": "Returns every store, with full details, ordered by identifier.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Stores returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Full definition of a store, returned by list/get/create/update endpoints.",
                    "$ref": "#/components/schemas/StoreDefinition"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Full definition of a store, returned by list/get/create/update endpoints.",
                    "$ref": "#/components/schemas/StoreDefinition"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "Full definition of a store, returned by list/get/create/update endpoints.",
                    "$ref": "#/components/schemas/StoreDefinition"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.dataStore:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.dataStore:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Stores"
        ],
        "summary": "Create a new store",
        "description": "Adds a new physical store location to the tenant.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Identifier and details of the new store.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to create a store.",
                "$ref": "#/components/schemas/CreateStoreRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to create a store.",
                "$ref": "#/components/schemas/CreateStoreRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to create a store.",
                "$ref": "#/components/schemas/CreateStoreRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "201": {
            "description": "Store created.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of a store, returned by list/get/create/update endpoints.",
                  "$ref": "#/components/schemas/StoreDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of a store, returned by list/get/create/update endpoints.",
                  "$ref": "#/components/schemas/StoreDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of a store, returned by list/get/create/update endpoints.",
                  "$ref": "#/components/schemas/StoreDefinition"
                }
              }
            }
          },
          "400": {
            "description": "A required field is missing, a coordinate is out of range, a name is longer than 200 characters, or the store identifier has a forbidden character.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.dataStore:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "A store with this identifier already exists, in any case.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.dataStore:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/stores/{storeId}": {
      "delete": {
        "tags": [
          "Stores"
        ],
        "summary": "Delete a store",
        "description": "Removes the store from the tenant. Holders whose `storeId` refers to it are\nnot changed.",
        "parameters": [
          {
            "name": "storeId",
            "in": "path",
            "description": "Identifier of the store, matched case-insensitively.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Store deleted."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.dataStore:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Store not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.dataStore:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Stores"
        ],
        "summary": "Get a specific store",
        "description": "Returns the full definition of the store identified by storeId.",
        "parameters": [
          {
            "name": "storeId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Store returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of a store, returned by list/get/create/update endpoints.",
                  "$ref": "#/components/schemas/StoreDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of a store, returned by list/get/create/update endpoints.",
                  "$ref": "#/components/schemas/StoreDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of a store, returned by list/get/create/update endpoints.",
                  "$ref": "#/components/schemas/StoreDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.dataStore:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Store not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.dataStore:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Stores"
        ],
        "summary": "Update an existing store",
        "description": "Replaces every field of the store but its identifier: a field left out is cleared, not kept.",
        "parameters": [
          {
            "name": "storeId",
            "in": "path",
            "description": "Identifier of the store, matched case-insensitively.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Every field of the store but its identifier.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to update a store. Fully replaces the store's fields other than its identifier.",
                "$ref": "#/components/schemas/UpdateStoreRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to update a store. Fully replaces the store's fields other than its identifier.",
                "$ref": "#/components/schemas/UpdateStoreRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to update a store. Fully replaces the store's fields other than its identifier.",
                "$ref": "#/components/schemas/UpdateStoreRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Store updated.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Full definition of a store, returned by list/get/create/update endpoints.",
                  "$ref": "#/components/schemas/StoreDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Full definition of a store, returned by list/get/create/update endpoints.",
                  "$ref": "#/components/schemas/StoreDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Full definition of a store, returned by list/get/create/update endpoints.",
                  "$ref": "#/components/schemas/StoreDefinition"
                }
              }
            }
          },
          "400": {
            "description": "A required field is missing, a coordinate is out of range, or a name is longer than 200 characters.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.dataStore:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Store not found.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.dataStore:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/users": {
      "get": {
        "tags": [
          "Users"
        ],
        "summary": "List all users attached to the tenant",
        "description": "Returns every back-office user holding access to this tenant, invitations not yet activated included\n(their `lastLogin` is null).",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Users returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A back-office user, as seen from this tenant.",
                    "$ref": "#/components/schemas/TenantUser"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A back-office user, as seen from this tenant.",
                    "$ref": "#/components/schemas/TenantUser"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A back-office user, as seen from this tenant.",
                    "$ref": "#/components/schemas/TenantUser"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.access:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.access:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Users"
        ],
        "summary": "Create a new user or attach an existing user to the tenant, unless already attached",
        "description": "Creates a new user or attaches an existing one to this tenant. If the user already has access to\nthe tenant with a valid role, returns HTTP 409 Conflict - unless the user has never signed in, in which\ncase the role is updated to the requested one and a new invitation link is sent: this lets an admin\nretry after a failed send, or correct the role before the invitee activates.\n            \nWhat the user receives depends on the account: a new account, or one that has never set a password,\ngets an invitation e-mail with an activation link (see the invitation endpoints); an account already\nin use on another tenant gets an \"access granted\" e-mail and signs in as usual.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Who to invite and the role to grant on the tenant.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request payload for inviting a user to the tenant.",
                "$ref": "#/components/schemas/CreateTenantUserRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request payload for inviting a user to the tenant.",
                "$ref": "#/components/schemas/CreateTenantUserRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request payload for inviting a user to the tenant.",
                "$ref": "#/components/schemas/CreateTenantUserRequest"
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "User created or attached, and the e-mail sent.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A back-office user, as seen from this tenant.",
                  "$ref": "#/components/schemas/TenantUser"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A back-office user, as seen from this tenant.",
                  "$ref": "#/components/schemas/TenantUser"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A back-office user, as seen from this tenant.",
                  "$ref": "#/components/schemas/TenantUser"
                }
              }
            }
          },
          "400": {
            "description": "E-mail or role is missing, the role does not exist on this tenant, or the name is longer than 200 characters.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.access:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "User already has access to tenant and has signed in at least once.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.access:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/users/{userId}": {
      "delete": {
        "tags": [
          "Users"
        ],
        "summary": "Remove a user from the tenant",
        "description": "Removes the tenant access from the user but keeps the account, with its access to other tenants.\nA pending invitation link stops working. Idempotent: an unknown user id is also answered with 204.",
        "parameters": [
          {
            "name": "userId",
            "in": "path",
            "description": "User id, as returned in `id`.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "User removed from tenant, or no such user."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.access:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.access:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "get": {
        "tags": [
          "Users"
        ],
        "summary": "Get a user attached to the tenant",
        "description": "Returns the back-office user details for the requested tenant.",
        "parameters": [
          {
            "name": "userId",
            "in": "path",
            "description": "User id, as returned in `id`.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "User returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A back-office user, as seen from this tenant.",
                  "$ref": "#/components/schemas/TenantUser"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A back-office user, as seen from this tenant.",
                  "$ref": "#/components/schemas/TenantUser"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A back-office user, as seen from this tenant.",
                  "$ref": "#/components/schemas/TenantUser"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.access:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No such user, or the user has no access to this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.access:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "Users"
        ],
        "summary": "Update a user attached to the tenant",
        "description": "Replaces the user's role on this tenant and, when `name` is sent, their display name. No e-mail is\nsent.",
        "parameters": [
          {
            "name": "userId",
            "in": "path",
            "description": "User id, as returned in `id`.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Role to hold on this tenant and, optionally, a new display name.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request payload for updating a tenant user.",
                "$ref": "#/components/schemas/UpdateTenantUserRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request payload for updating a tenant user.",
                "$ref": "#/components/schemas/UpdateTenantUserRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request payload for updating a tenant user.",
                "$ref": "#/components/schemas/UpdateTenantUserRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "User updated.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A back-office user, as seen from this tenant.",
                  "$ref": "#/components/schemas/TenantUser"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A back-office user, as seen from this tenant.",
                  "$ref": "#/components/schemas/TenantUser"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A back-office user, as seen from this tenant.",
                  "$ref": "#/components/schemas/TenantUser"
                }
              }
            }
          },
          "400": {
            "description": "Role is missing or does not exist on this tenant, or the name is longer than 200 characters.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.access:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No such user, or the user has no access to this tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.access:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/users/me": {
      "get": {
        "tags": [
          "Users"
        ],
        "summary": "Get current authenticated user for the tenant",
        "description": "Returns profile information and fully-expanded permissions for the current authenticated back-office user.\n            \n- If caller is global administrator, all permissions are returned.\n- If role contains wildcard permissions (`*` or `area:*`), values are expanded.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Current user returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "The signed-in user, as seen from this tenant.",
                  "$ref": "#/components/schemas/CurrentTenantUser"
                }
              },
              "application/json": {
                "schema": {
                  "description": "The signed-in user, as seen from this tenant.",
                  "$ref": "#/components/schemas/CurrentTenantUser"
                }
              },
              "text/json": {
                "schema": {
                  "description": "The signed-in user, as seen from this tenant.",
                  "$ref": "#/components/schemas/CurrentTenantUser"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.core:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.core:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/wallet/google/classes": {
      "get": {
        "tags": [
          "GoogleClassesAdmin"
        ],
        "summary": "Lists the tenant's Google Wallet classes of one family, for the current environment.",
        "parameters": [
          {
            "name": "type",
            "in": "query",
            "description": "Class family to list.",
            "schema": {
              "description": "The Google Wallet class family to read; each family is a separate collection at Google:\n`Loyalty` (loyalty cards), `GiftCard`, `Offer` (coupons), `EventTicket`, `Generic`.",
              "$ref": "#/components/schemas/GoogleClassType"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The classes; empty when the issuer has none of that family.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A Google Wallet class registered under the tenant's issuer.",
                    "$ref": "#/components/schemas/GoogleClassResponse"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A Google Wallet class registered under the tenant's issuer.",
                    "$ref": "#/components/schemas/GoogleClassResponse"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A Google Wallet class registered under the tenant's issuer.",
                    "$ref": "#/components/schemas/GoogleClassResponse"
                  }
                }
              }
            }
          },
          "400": {
            "description": "The `type` query parameter is missing or unknown.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.walletConfig:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Google Wallet is not configured for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.walletConfig:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/wallet/google/classes/loyalty/discoverable-program": {
      "get": {
        "tags": [
          "GoogleClassesAdmin"
        ],
        "summary": "Reads one loyalty class and its discoverable program.",
        "description": "The class is returned even when it publishes no discoverable program; the program fields are then null. Any class of the issuer can be read, whatever its environment.",
        "parameters": [
          {
            "name": "classId",
            "in": "query",
            "description": "Full Google class id.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The class and its discoverable program.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A loyalty class and the discoverable program it publishes in the Google Wallet app.",
                  "$ref": "#/components/schemas/DiscoverableProgramResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A loyalty class and the discoverable program it publishes in the Google Wallet app.",
                  "$ref": "#/components/schemas/DiscoverableProgramResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A loyalty class and the discoverable program it publishes in the Google Wallet app.",
                  "$ref": "#/components/schemas/DiscoverableProgramResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.walletConfig:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Google Wallet is not configured for the tenant, or Google has no loyalty class with this id.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.walletConfig:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "GoogleClassesAdmin"
        ],
        "summary": "Creates the loyalty class carrying a discoverable program, or replaces the program on an existing one.",
        "description": "On an existing class, the fields this endpoint does not manage (colors, labels, tiers) are kept, except\nthe class template, security animation, unlock requirement, notification preference and value-added\nmodules, which are reset; the program's publication state is kept. A new class starts in the state Google assigns, trusted\ntesters only; going live is done at Google, not here. Every call resubmits the class for Google's review\n(`UNDER_REVIEW`).",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The discoverable program.",
          "content": {
            "application/json": {
              "schema": {
                "description": "The discoverable program to publish on a loyalty class.",
                "$ref": "#/components/schemas/DiscoverableProgramRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "The discoverable program to publish on a loyalty class.",
                "$ref": "#/components/schemas/DiscoverableProgramRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "The discoverable program to publish on a loyalty class.",
                "$ref": "#/components/schemas/DiscoverableProgramRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "The class as Google stored it.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "A loyalty class and the discoverable program it publishes in the Google Wallet app.",
                  "$ref": "#/components/schemas/DiscoverableProgramResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "A loyalty class and the discoverable program it publishes in the Google Wallet app.",
                  "$ref": "#/components/schemas/DiscoverableProgramResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "A loyalty class and the discoverable program it publishes in the Google Wallet app.",
                  "$ref": "#/components/schemas/DiscoverableProgramResponse"
                }
              }
            }
          },
          "400": {
            "description": "A required field is missing, or Google Wallet refuses a value (for example the country code or the logo URL).",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.walletConfig:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Google Wallet is not configured for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.walletConfig:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/wallet/google/classes/loyalty/discoverable-programs": {
      "get": {
        "tags": [
          "GoogleClassesAdmin"
        ],
        "summary": "Lists the loyalty classes of the current environment that publish a discoverable program.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The discoverable programs; empty when none is configured.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A loyalty class and the discoverable program it publishes in the Google Wallet app.",
                    "$ref": "#/components/schemas/DiscoverableProgramResponse"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A loyalty class and the discoverable program it publishes in the Google Wallet app.",
                    "$ref": "#/components/schemas/DiscoverableProgramResponse"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A loyalty class and the discoverable program it publishes in the Google Wallet app.",
                    "$ref": "#/components/schemas/DiscoverableProgramResponse"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.walletConfig:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Google Wallet is not configured for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.walletConfig:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/wallet/google/classes/pass-count": {
      "get": {
        "tags": [
          "GoogleClassesAdmin"
        ],
        "summary": "Counts the Google Wallet passes (objects) issued on a class.",
        "description": "Counts every object on the class, saved by a holder or not; slow on large classes. The count can lag\nrecent changes by a few minutes.",
        "parameters": [
          {
            "name": "classId",
            "in": "query",
            "description": "Full Google class id, as returned by the list endpoint.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "type",
            "in": "query",
            "description": "Family of the class; it must be the family the class belongs to.",
            "schema": {
              "description": "The Google Wallet class family to read; each family is a separate collection at Google:\n`Loyalty` (loyalty cards), `GiftCard`, `Offer` (coupons), `EventTicket`, `Generic`.",
              "$ref": "#/components/schemas/GoogleClassType"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The number of objects on the class.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "integer",
                  "format": "int32"
                }
              },
              "application/json": {
                "schema": {
                  "type": "integer",
                  "format": "int32"
                }
              },
              "text/json": {
                "schema": {
                  "type": "integer",
                  "format": "int32"
                }
              }
            }
          },
          "400": {
            "description": "The `type` query parameter is missing or unknown.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.walletConfig:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Google Wallet is not configured for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.walletConfig:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/walletProviders/apple": {
      "get": {
        "tags": [
          "AppleWalletProvider"
        ],
        "summary": "Get Apple Wallet provider settings",
        "description": "Returns the Apple Wallet fields. Private key material is never returned; only a\npresence flag (`hasValue`/`hasKey`) indicates whether it is currently set. Omit the\ncorresponding field on `PUT` to keep the currently configured private key material unchanged.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Settings returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Apple Wallet provider settings.",
                  "$ref": "#/components/schemas/AppleWalletProviderDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Apple Wallet provider settings.",
                  "$ref": "#/components/schemas/AppleWalletProviderDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Apple Wallet provider settings.",
                  "$ref": "#/components/schemas/AppleWalletProviderDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.walletProvider:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Apple Wallet is not configured.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.walletProvider:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "AppleWalletProvider"
        ],
        "summary": "Configure Apple Wallet provider settings",
        "description": "Replaces the wallet fields, leaving the \"Sign in with Apple\" `serviceIdentifier` field\nuntouched. An omitted or null `webServiceUrl` or `pass.certificateRequest` is cleared, not\nkept.\n            \nThe pass certificate, its private key and the push notification key must belong to the Apple Developer\nteam identified by `teamIdentifier`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Apple Wallet settings to store.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to configure Apple Wallet.",
                "$ref": "#/components/schemas/UpdateAppleWalletProviderRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to configure Apple Wallet.",
                "$ref": "#/components/schemas/UpdateAppleWalletProviderRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to configure Apple Wallet.",
                "$ref": "#/components/schemas/UpdateAppleWalletProviderRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Settings updated.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Apple Wallet provider settings.",
                  "$ref": "#/components/schemas/AppleWalletProviderDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Apple Wallet provider settings.",
                  "$ref": "#/components/schemas/AppleWalletProviderDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Apple Wallet provider settings.",
                  "$ref": "#/components/schemas/AppleWalletProviderDefinition"
                }
              }
            }
          },
          "400": {
            "description": "A required field is missing, or a private key field (APNs key, certificate, or certificate request) was omitted and none is currently configured.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.walletProvider:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.walletProvider:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/walletProviders/google": {
      "get": {
        "tags": [
          "GoogleWalletProvider"
        ],
        "summary": "Get Google Wallet provider settings",
        "description": "Returns the Google Wallet issuer settings. Private key material is never returned;\nonly a presence flag (`hasPrivateKey`/`hasClientSecret`/`hasRefreshToken`) indicates\nwhether it is currently set. Omit `credential.privateKey` on `PUT` to keep the currently\nconfigured private key unchanged.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Settings returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Google Wallet provider settings.",
                  "$ref": "#/components/schemas/GoogleWalletProviderDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Google Wallet provider settings.",
                  "$ref": "#/components/schemas/GoogleWalletProviderDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Google Wallet provider settings.",
                  "$ref": "#/components/schemas/GoogleWalletProviderDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.walletProvider:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Google Wallet is not configured.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.walletProvider:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "GoogleWalletProvider"
        ],
        "summary": "Configure Google Wallet provider settings",
        "description": "Replaces the Google Wallet issuer settings, leaving the \"Sign in with Google\" settings and the rotating\nbarcode settings untouched. An omitted or null `webServiceUrl` or `credential.quotaProject` is\ncleared, not kept.\n            \nThe credential must be a service account key with access to the issuer account `issuerId`.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Google Wallet settings to store.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to configure Google Wallet.",
                "$ref": "#/components/schemas/UpdateGoogleWalletProviderRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to configure Google Wallet.",
                "$ref": "#/components/schemas/UpdateGoogleWalletProviderRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to configure Google Wallet.",
                "$ref": "#/components/schemas/UpdateGoogleWalletProviderRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Settings updated.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Google Wallet provider settings.",
                  "$ref": "#/components/schemas/GoogleWalletProviderDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Google Wallet provider settings.",
                  "$ref": "#/components/schemas/GoogleWalletProviderDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Google Wallet provider settings.",
                  "$ref": "#/components/schemas/GoogleWalletProviderDefinition"
                }
              }
            }
          },
          "400": {
            "description": "A required field is missing, or no private key was supplied and none is currently configured.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.walletProvider:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.walletProvider:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/admin/walletProviders/google/rotatingBarcode": {
      "get": {
        "tags": [
          "GoogleWalletProvider"
        ],
        "summary": "Get rotating barcode settings",
        "description": "The secret is never returned: `hasSecret` says whether one is set. Without one, a template cannot use\na rotating barcode. Before the first save, the defaults are returned (30 seconds, 8 digits). Requires the\n`tenant.passType:read` scope, so the pass template editor can offer rotating barcodes.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Settings returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Settings of rotating barcodes, which show a time-based one-time password. A scanner needs the secret,\nthe period and the digits.",
                  "$ref": "#/components/schemas/RotatingBarcodeDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Settings of rotating barcodes, which show a time-based one-time password. A scanner needs the secret,\nthe period and the digits.",
                  "$ref": "#/components/schemas/RotatingBarcodeDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Settings of rotating barcodes, which show a time-based one-time password. A scanner needs the secret,\nthe period and the digits.",
                  "$ref": "#/components/schemas/RotatingBarcodeDefinition"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.passType:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.passType:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "put": {
        "tags": [
          "GoogleWalletProvider"
        ],
        "summary": "Configure rotating barcode settings",
        "description": "Leaves the Google Wallet credentials untouched. Google Wallet must be\nconfigured first. Passes are not updated by this call: a pass keeps its current codes until it is\nregenerated.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Rotating barcode settings to store.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to configure rotating barcodes.",
                "$ref": "#/components/schemas/UpdateRotatingBarcodeRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to configure rotating barcodes.",
                "$ref": "#/components/schemas/UpdateRotatingBarcodeRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to configure rotating barcodes.",
                "$ref": "#/components/schemas/UpdateRotatingBarcodeRequest"
              }
            }
          },
          "required": true
        },
        "responses": {
          "200": {
            "description": "Settings updated.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Settings of rotating barcodes, which show a time-based one-time password. A scanner needs the secret,\nthe period and the digits.",
                  "$ref": "#/components/schemas/RotatingBarcodeDefinition"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Settings of rotating barcodes, which show a time-based one-time password. A scanner needs the secret,\nthe period and the digits.",
                  "$ref": "#/components/schemas/RotatingBarcodeDefinition"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Settings of rotating barcodes, which show a time-based one-time password. A scanner needs the secret,\nthe period and the digits.",
                  "$ref": "#/components/schemas/RotatingBarcodeDefinition"
                }
              }
            }
          },
          "400": {
            "description": "A value is out of range, or no secret was supplied and none is currently configured.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.configuration.walletProvider:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Google Wallet is not configured.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.configuration.walletProvider:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/cachedContent/{key}": {
      "get": {
        "tags": [
          "CachedContent"
        ],
        "summary": "Downloads one stored file of the tenant.",
        "description": "The response carries the file's content type. A file stays available for one year after it is\ngenerated; after that the URL returns 404.",
        "parameters": [
          {
            "name": "key",
            "in": "path",
            "description": "Key of the file, as it appears in the URL the platform generated; may contain `/`.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "File returned."
          },
          "404": {
            "description": "No file exists under this key for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/external/livestore": {
      "get": {
        "tags": [
          "Cegid"
        ],
        "summary": "Open the customer form for a LiveStore session",
        "description": "Where LiveStore sends the associate's browser. Redirects to the tenant's LiveStore customer form, opened\nfor the session's customer, passing on every other query parameter. In tablet mode, the form opens in\ntablet mode.\n            \nA `storeId` value of the form `530?sessionId=xxx` is read as `storeId=530` and\n`sessionId=xxx`.",
        "parameters": [
          {
            "name": "model",
            "in": "query",
            "description": "Every query parameter. `sessionId` identifies the session opened with a POST to `session`.",
            "style": "deepObject",
            "schema": {
              "type": "object",
              "additionalProperties": {
                "type": "string"
              }
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "No `sessionId` was sent (connection check); nothing is done."
          },
          "302": {
            "description": "Redirect to the customer form."
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "503": {
            "description": "LiveStore is enabled but not configured for this tenant."
          }
        }
      }
    },
    "/api/{tenantId}/external/livestore/session": {
      "get": {
        "tags": [
          "Cegid"
        ],
        "summary": "Check the connection",
        "description": "Lets LiveStore check, with GET or HEAD, that the session endpoint is reachable. Has no effect.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "The endpoint is reachable."
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      },
      "head": {
        "tags": [
          "Cegid"
        ],
        "summary": "Check the connection",
        "description": "Lets LiveStore check, with GET or HEAD, that the session endpoint is reachable. Has no effect.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "The endpoint is reachable."
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      },
      "post": {
        "tags": [
          "Cegid"
        ],
        "summary": "Open a LiveStore session for a customer",
        "description": "Called by Cegid LiveStore before it sends the associate to the form. The session is valid for one hour from\nthis call; posting again under the same sessionId replaces the customer and restarts the\nhour. An expired session no longer opens the form.",
        "parameters": [
          {
            "name": "sessionId",
            "in": "query",
            "description": "Identifier LiveStore chose for the session; the form is later opened with it. Required.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "storeId",
            "in": "query",
            "description": "Store the session is opened in. When sent, replaces `storeId` of the body.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The customer the session is opened for.",
          "content": {
            "application/json": {
              "schema": {
                "description": "The customer a Cegid LiveStore session is opened for.",
                "$ref": "#/components/schemas/CustomerPayload"
              }
            },
            "text/json": {
              "schema": {
                "description": "The customer a Cegid LiveStore session is opened for.",
                "$ref": "#/components/schemas/CustomerPayload"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "The customer a Cegid LiveStore session is opened for.",
                "$ref": "#/components/schemas/CustomerPayload"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Session stored."
          },
          "400": {
            "description": "`sessionId` or `callbackUrl` is missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.livestore.access:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.livestore.access:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/external/secutix/orders/getTicketsUrl/{fileId}": {
      "get": {
        "tags": [
          "Secutix"
        ],
        "summary": "Get the public tickets page URL of the Secutix order behind a file.",
        "description": "Returns, as plain text, the absolute URL of the tenant's public tickets page for the first order of the\nSecutix file (`…/{tenantId}/tickets?ids.secutix.orderToken={orderToken}`). That page is where the\nholder adds the order's tickets to a wallet.",
        "parameters": [
          {
            "name": "fileId",
            "in": "path",
            "description": "Secutix file identifier.",
            "required": true,
            "schema": {
              "type": "integer",
              "format": "int64"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "URL of the tickets page."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.secutix.order:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Secutix is not configured for the tenant, or Secutix has no order for the file.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.secutix.order:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/passes/apple/{version}/devices/{deviceIdentifier}/registrations/{passTypeIdentifier}": {
      "get": {
        "tags": [
          "ApplePass"
        ],
        "summary": "Lists the passes registered on a device that changed since the device last asked, so that it downloads\nthem again.",
        "description": "Follows Apple's specification. The body is\n`{ \"lastUpdated\": \"{tag}\", \"serialNumbers\": [...] }`, where the tag (milliseconds since the Unix epoch,\nthe latest change among the listed passes) is what the device sends back as `passesUpdatedSince`.\nA pass with no recorded change is always listed.",
        "parameters": [
          {
            "name": "deviceIdentifier",
            "in": "path",
            "description": "Apple's id of the device.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "passTypeIdentifier",
            "in": "path",
            "description": "Apple pass type identifier; only passes registered under it are considered.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "passesUpdatedSince",
            "in": "query",
            "description": "Query `passesUpdatedSince`: the `lastUpdated` tag of the previous answer. Omitted, every\nregistered pass is listed.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "version",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The passes that changed."
          },
          "204": {
            "description": "The device has no registered pass, or none changed since the tag."
          },
          "400": {
            "description": "The tag is not an integer.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 6000 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/passes/apple/{version}/devices/{deviceIdentifier}/registrations/{passTypeIdentifier}/{serialNumber}": {
      "delete": {
        "tags": [
          "ApplePass"
        ],
        "summary": "Records that a holder removed the pass from Apple Wallet on a device; the device gets no further updates.",
        "description": "Updates the pass's installation counts and, when this removes a registered device, emits a\npass-uninstalled event.",
        "parameters": [
          {
            "name": "deviceIdentifier",
            "in": "path",
            "description": "Apple's id of the device.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "passTypeIdentifier",
            "in": "path",
            "description": "Apple pass type identifier of the pass.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "serialNumber",
            "in": "path",
            "description": "Pass id.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "version",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The device is no longer registered for the pass."
          },
          "401": {
            "description": "The `ApplePass` token is missing or does not match the pass.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No pass has this serial number.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 6000 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            }
          }
        }
      },
      "post": {
        "tags": [
          "ApplePass"
        ],
        "summary": "Records that a holder added the pass to Apple Wallet on a device, so that the device receives its updates.",
        "description": "A first registration of the device updates the pass's installation counts and emits a pass-installed\nevent carrying the source the pass was downloaded from. A known device with a new push token has its\ntoken replaced; a known push token under a new device id is registered and the pass is pushed again.",
        "parameters": [
          {
            "name": "deviceIdentifier",
            "in": "path",
            "description": "Apple's id of the device.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "passTypeIdentifier",
            "in": "path",
            "description": "Apple pass type identifier of the pass.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "serialNumber",
            "in": "path",
            "description": "Pass id.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "version",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Apple's body: `{ \"pushToken\": \"...\" }`, the token pushes to this device are sent with.",
          "content": {
            "application/json": {
              "schema": { }
            },
            "text/json": {
              "schema": { }
            },
            "application/*+json": {
              "schema": { }
            }
          }
        },
        "responses": {
          "200": {
            "description": "The device was already registered; its push token is up to date."
          },
          "201": {
            "description": "The device is now registered, or re-registered under a new device id."
          },
          "400": {
            "description": "`pushToken` is missing or empty.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The `ApplePass` token is missing or does not match the pass.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No pass has this serial number.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 6000 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/passes/apple/{version}/log": {
      "post": {
        "tags": [
          "ApplePass"
        ],
        "summary": "Receives the error messages Apple devices report about the web service (failed downloads, rejected\nsignatures, malformed passes).",
        "description": "Follows Apple's specification. The messages are not linked to a pass or device.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "version",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Apple's body: `{ \"logs\": [\"...\", \"...\"] }`. Without `logs`, nothing is recorded.",
          "content": {
            "application/json": {
              "schema": { }
            },
            "text/json": {
              "schema": { }
            },
            "application/*+json": {
              "schema": { }
            }
          }
        },
        "responses": {
          "200": {
            "description": "The messages were received."
          },
          "429": {
            "description": "Over 100000 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/passes/apple/{version}/passes/{passTypeIdentifier}/{serialNumber}": {
      "get": {
        "tags": [
          "ApplePass"
        ],
        "summary": "Downloads the current `.pkpass` of a pass for a device that holds it.",
        "description": "Answers 304 when `If-Modified-Since` is less than 10 seconds old and the pass has not changed\nsince; otherwise returns the current pass, with `Last-Modified` set to the time of the response.",
        "parameters": [
          {
            "name": "passTypeIdentifier",
            "in": "path",
            "description": "Apple pass type identifier of the pass.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "serialNumber",
            "in": "path",
            "description": "Pass id.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "version",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "The `.pkpass` file.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "application/json": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "text/json": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              }
            }
          },
          "304": {
            "description": "The pass has not changed since `If-Modified-Since`, sent less than 10 seconds ago."
          },
          "400": {
            "description": "The serial number is blank.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The `ApplePass` token is missing or does not match the pass.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No pass has this serial number.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 6000 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/passes/google": {
      "post": {
        "tags": [
          "GooglePass"
        ],
        "summary": "Records that a holder added a pass to Google Wallet or removed it.",
        "description": "Called by Google, not by tenants. `save` increments the pass's Google installation count (setting\nthe Google installation date on the first one), increments its active and total installation counts,\nand emits a pass-installed event carrying the source the pass was downloaded from.\n`del` decrements the Google count; when it reaches zero the pass is no longer counted as saved in\nGoogle Wallet and a pass-uninstalled event is emitted. A message already processed, recognised by its\nnonce, changes nothing.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "Google's callback envelope. Its `signedMessage` field is a JSON string carrying `classId`, `objectId` (`{issuerId}.{passId}`), `eventType` (`save` or `del`) and `nonce`.",
          "content": {
            "application/json": {
              "schema": { }
            },
            "text/json": {
              "schema": { }
            },
            "application/*+json": {
              "schema": { }
            }
          }
        },
        "responses": {
          "200": {
            "description": "The installation change was recorded."
          },
          "202": {
            "description": "A `del` for a pass that is no longer on record; nothing changes."
          },
          "204": {
            "description": "Nothing to record: `signedMessage` is missing or has no nonce, or the message was already processed."
          },
          "400": {
            "description": "`signedMessage` is not JSON, or its event type is neither `save` nor `del`; Google need not retry it.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No pass has the id taken from `objectId`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/passes/google/signin": {
      "get": {
        "tags": [
          "GooglePass"
        ],
        "summary": "Sends a Google Wallet user who tapped \"Sign in\" on a loyalty program to the tenant's sign-in page,\npre-filled with any profile Google shares.",
        "description": "Google documents a form `POST` carrying `SharedDataType`; Google Wallet also issues a bare\n`GET`, so both are accepted. Emits a discoverable-program sign-in event, then redirects to\n`{public site}/{tenantId}/{url}` with the profile keys renamed as on the sign-up endpoint.",
        "parameters": [
          {
            "name": "url",
            "in": "query",
            "description": "Query `url`: the page path under the tenant to redirect to, set in the Google class's sign-in URL.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "SharedDataType",
            "in": "query",
            "description": "Query `SharedDataType`: the profile as Base64Url-encoded JSON. Wins over the form field.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "multipart/form-data": {
              "schema": {
                "type": "object",
                "properties": {
                  "SharedDataType": {
                    "type": "string",
                    "description": "Form field `SharedDataType`: the profile as Base64Url-encoded JSON."
                  }
                }
              },
              "encoding": {
                "SharedDataType": {
                  "style": "form"
                }
              }
            }
          }
        },
        "responses": {
          "302": {
            "description": "Redirect to the sign-in page with the profile as query parameters."
          },
          "400": {
            "description": "The profile is not valid Base64Url-encoded JSON of string values.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      },
      "post": {
        "tags": [
          "GooglePass"
        ],
        "summary": "Sends a Google Wallet user who tapped \"Sign in\" on a loyalty program to the tenant's sign-in page,\npre-filled with any profile Google shares.",
        "description": "Google documents a form `POST` carrying `SharedDataType`; Google Wallet also issues a bare\n`GET`, so both are accepted. Emits a discoverable-program sign-in event, then redirects to\n`{public site}/{tenantId}/{url}` with the profile keys renamed as on the sign-up endpoint.",
        "parameters": [
          {
            "name": "url",
            "in": "query",
            "description": "Query `url`: the page path under the tenant to redirect to, set in the Google class's sign-in URL.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "SharedDataType",
            "in": "query",
            "description": "Query `SharedDataType`: the profile as Base64Url-encoded JSON. Wins over the form field.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "multipart/form-data": {
              "schema": {
                "type": "object",
                "properties": {
                  "SharedDataType": {
                    "type": "string",
                    "description": "Form field `SharedDataType`: the profile as Base64Url-encoded JSON."
                  }
                }
              },
              "encoding": {
                "SharedDataType": {
                  "style": "form"
                }
              }
            }
          }
        },
        "responses": {
          "302": {
            "description": "Redirect to the sign-in page with the profile as query parameters."
          },
          "400": {
            "description": "The profile is not valid Base64Url-encoded JSON of string values.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/passes/google/signup": {
      "post": {
        "tags": [
          "GooglePass"
        ],
        "summary": "Sends a Google Wallet user who tapped \"Sign up\" on a loyalty program to the tenant's sign-up page,\npre-filled with the profile Google shares.",
        "description": "Posted by Google Wallet's WebView (discoverable program merchant sign-up flow) as a form. Emits a\ndiscoverable-program sign-up event, then redirects to `{public site}/{tenantId}/{url}` with the\nprofile as query parameters. Google's keys, camelCase or legacy UPPER_SNAKE_CASE, are renamed:\n`firstName`, `lastName`, `address` (from `addressLine1`/`STREET_ADDRESS`),\n`city`, `zipCode`, `country`, `email`, `phoneNumber` (from `phone`/`PHONE`).\nOther keys are forwarded unchanged. Every profile field is optional.",
        "parameters": [
          {
            "name": "url",
            "in": "query",
            "description": "Query `url`: the page path under the tenant to redirect to, set in the Google class's sign-up URL.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "content": {
            "multipart/form-data": {
              "schema": {
                "type": "object",
                "properties": {
                  "SharedDataType": {
                    "type": "string",
                    "description": "Form field `SharedDataType`: the profile as Base64Url-encoded JSON, the field Google sends for loyalty classes."
                  },
                  "userProfile": {
                    "type": "string",
                    "description": "Form field `userProfile`: read only when `SharedDataType` is absent; the name Google's offer enrollment guide uses for the same profile."
                  }
                }
              },
              "encoding": {
                "SharedDataType": {
                  "style": "form"
                },
                "userProfile": {
                  "style": "form"
                }
              }
            }
          }
        },
        "responses": {
          "302": {
            "description": "Redirect to the sign-up page with the profile as query parameters."
          },
          "400": {
            "description": "The profile is not valid Base64Url-encoded JSON of string values.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/webhooks/listeners/actito/custom-actions/updatePass": {
      "post": {
        "tags": [
          "Actito"
        ],
        "summary": "Write a value on a holder's passes from an Actito scenario",
        "description": "Called by Actito when the integration's custom action runs. Finds every pass whose\n`twcExternalIdentifier` identifier equals the profile's `actitoExternalIdentifier` attribute,\nsets the `actito_{key}` additional data to the action's value, saves each pass and pushes it to the\nwallets, then posts to the action's `notifyOK` callback.\n            \nA 4xx means the message cannot be processed as configured, so Actito stops retrying it; a 5xx is retried.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The custom action message, read as a Neo.Extensions.Actito.ListenerController.CustomActionMessage.",
          "content": {
            "application/json": {
              "schema": { }
            },
            "text/json": {
              "schema": { }
            },
            "application/*+json": {
              "schema": { }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Passes updated and Actito notified; also when no pass matches the holder."
          },
          "400": {
            "description": "The message has no readable `data`, no `notifyOK` link, a pass template unknown to this tenant, or no string or number `profileAttributes.{actitoExternalIdentifier}` value.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.actito.listener:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.actito.listener:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/webhooks/listeners/actito/profile/{eventType}": {
      "post": {
        "tags": [
          "Actito"
        ],
        "summary": "Link a holder's passes to their Actito profile",
        "description": "Called by Actito when a profile is created, or when its `actitoExternalIdentifier` attribute changes.\nReads the profile from the profile table, finds the passes whose `twcExternalIdentifier` identifier\nequals that attribute, and records in the integration's wallet table in Actito the holder's most recently\ncreated Apple pass installed on a device and most recently created Google pass, each linked to the\nprofile. No pass is changed.\n            \nThe same event type, operation and profile received again within 2 hours answers 208 and is not\nprocessed again.",
        "parameters": [
          {
            "name": "eventType",
            "in": "path",
            "description": "Profile event Actito reports, from the route: `create` or `update`.",
            "required": true,
            "schema": {
              "description": "Profile table event Actito reports. The integration subscribes to both, the update one only for changes\nof the profile attribute named by `actitoExternalIdentifier`.",
              "$ref": "#/components/schemas/ProfileEventType"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The Actito event, carrying the profile identifier.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Envelope of an Actito profile webhook.",
                "$ref": "#/components/schemas/ActitoWrapper_NewProfile"
              }
            },
            "text/json": {
              "schema": {
                "description": "Envelope of an Actito profile webhook.",
                "$ref": "#/components/schemas/ActitoWrapper_NewProfile"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Envelope of an Actito profile webhook.",
                "$ref": "#/components/schemas/ActitoWrapper_NewProfile"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Event processed; also when no pass matches the profile."
          },
          "208": {
            "description": "The same event was already received within the last 2 hours; nothing is done."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.actito.listener:write</c> scope, or the endpoint is not enabled for the tenant.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.actito.listener:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/webhooks/listeners/cegid/{connectionId}": {
      "get": {
        "tags": [
          "Cegid"
        ],
        "summary": "List the Y2 business notification subscriptions",
        "description": "Returns every subscription Y2 reports as active for the connection's database, this platform's own\nincluded, to check where Y2 sends its notifications.",
        "parameters": [
          {
            "name": "connectionId",
            "in": "path",
            "description": "`name` of the Y2 connection whose database is read.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Subscriptions returned, possibly none.",
            "content": {
              "text/plain": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A Y2 business notification subscription: where Y2 sends its notifications for a database, and which ones.",
                    "$ref": "#/components/schemas/SubscriptionInformation"
                  }
                }
              },
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A Y2 business notification subscription: where Y2 sends its notifications for a database, and which ones.",
                    "$ref": "#/components/schemas/SubscriptionInformation"
                  }
                }
              },
              "text/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "description": "A Y2 business notification subscription: where Y2 sends its notifications for a database, and which ones.",
                    "$ref": "#/components/schemas/SubscriptionInformation"
                  }
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.y2.listener:read</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Cegid Y2 is not configured for this tenant, or no Y2 connection has this name.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The connection has no business notification credentials; set\n            `businessNotificationSettings.webServiceCredentials` in the Cegid Y2 configuration.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.y2.listener:read"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      },
      "post": {
        "tags": [
          "Cegid"
        ],
        "summary": "Process Cegid Y2 business notifications",
        "description": "Called by Y2. `Header.EventSource` decides the handling; each recognised notification is re-emitted\nas a platform event:\n<list type=\"bullet\"><item>`…ThirdParties.Customers.ICustomerService.Create`: `Y2:BusinessNotification:CustomerCreated`;\npasses are not updated.</item><item>`…ThirdParties.Customers.ICustomerService.Update`: `Y2:BusinessNotification:CustomerUpdated`;\nthe passes whose `y2.customerId` identifier is `Body.Key.CustomerId` are updated.</item><item>`…ISaleAndSellersService.CreateReceipt`, `…Engine.RegisterSale`,\n`…Documents.Sales.ISaleService.Create` and `…ManagementService.CreateFrom`:\n`Y2:BusinessNotification:ReceiptCreated`; the passes of the sale document's customer are updated.\nA receipt on hold updates no pass. `Body.Key` may be wrapped in a second `Key`.</item><item>`…ILoyaltyEngineService.AddCardOperations`: `Y2:BusinessNotification:LoyaltyUpdated`; the\npasses of the card's customer are updated.</item><item>Any other source: `Y2:BusinessNotification:Generic`, with the body untouched.</item></list>\nBody properties are matched case-insensitively.",
        "parameters": [
          {
            "name": "connectionId",
            "in": "path",
            "description": "`name` of the Y2 connection the subscription was registered for.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The notification as Y2 sends it.",
          "content": {
            "application/json": {
              "schema": {
                "description": "A Y2 business notification as Y2 posts it, with its body left as raw JSON. Also the payload of the\n`Y2:BusinessNotification:Generic` event, emitted for an event source with no dedicated handling.",
                "$ref": "#/components/schemas/GenericEventData"
              }
            },
            "text/json": {
              "schema": {
                "description": "A Y2 business notification as Y2 posts it, with its body left as raw JSON. Also the payload of the\n`Y2:BusinessNotification:Generic` event, emitted for an event source with no dedicated handling.",
                "$ref": "#/components/schemas/GenericEventData"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "A Y2 business notification as Y2 posts it, with its body left as raw JSON. Also the payload of the\n`Y2:BusinessNotification:Generic` event, emitted for an event source with no dedicated handling.",
                "$ref": "#/components/schemas/GenericEventData"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Notification accepted and its event emitted."
          },
          "400": {
            "description": "The body cannot be read as the shape its event source requires.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.y2.listener:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Cegid Y2 is not configured for this tenant, or no Y2 connection has this name.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.y2.listener:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/webhooks/listeners/cegid/{connectionId}/Register": {
      "post": {
        "tags": [
          "Cegid"
        ],
        "summary": "Register the Y2 business notification subscription",
        "description": "Makes Y2 push its business notifications for the connection's database to this platform. As Y2 delivers\nto a single subscription, another enabled subscription on that database is disabled. This platform's\nsubscription is created or updated to call `…/webhooks/listeners/cegid/{connectionId}`.\nSaving the Cegid Y2 configuration does the same for every connection with\n`listenToBusinessNotification`.",
        "parameters": [
          {
            "name": "connectionId",
            "in": "path",
            "description": "`name` of the Y2 connection to register the subscription for.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Subscription registered."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the <c>tenant.y2.listener:write</c> scope.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "Cegid Y2 is not configured for this tenant, or no Y2 connection has this name.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The connection has no business notification credentials; set\n            `businessNotificationSettings.webServiceCredentials` in the Cegid Y2 configuration.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.y2.listener:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/webhooks/listeners/klaviyo/passes/pushUpdate": {
      "post": {
        "tags": [
          "Klaviyo"
        ],
        "summary": "Update a pass from a Klaviyo flow",
        "description": "Target of a Klaviyo flow webhook action. Finds the pass by `identifiers` and accepts an update with\nthe given pass template, additional data and metadata option; the pass is then updated and refreshed on\nthe holder's devices shortly after the answer.\n            \nSame changes as `PATCH /api/{tenantId}/passes` with `options.bypassQueue` false. The Klaviyo\nlistener must be enabled for the tenant.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The pass to update and the change to apply.",
          "content": {
            "application/json": {
              "schema": {
                "description": "The pass a Klaviyo webhook targets and the change to apply to it.",
                "$ref": "#/components/schemas/PushUpdateData"
              }
            },
            "text/json": {
              "schema": {
                "description": "The pass a Klaviyo webhook targets and the change to apply to it.",
                "$ref": "#/components/schemas/PushUpdateData"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "The pass a Klaviyo webhook targets and the change to apply to it.",
                "$ref": "#/components/schemas/PushUpdateData"
              }
            }
          }
        },
        "responses": {
          "202": {
            "description": "Update accepted."
          },
          "400": {
            "description": "The body is invalid, `id` is combined with other identifiers, or `passType` is not declared for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the `tenant.klaviyo.listener:write` scope, or the Klaviyo listener is not enabled for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "404": {
            "description": "No pass matches the identifiers.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.klaviyo.listener:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/webhooks/listeners/klaviyo/profiles/sync": {
      "post": {
        "tags": [
          "Klaviyo"
        ],
        "summary": "Synchronize Klaviyo customer profile",
        "description": "Accepts the request and answers at once, with no body; the synchronisation completes shortly after.\nThe holder is looked up by `email` and `phone_number` in the tenant's customer systems, then\nKlaviyo receives: a `Neostore - Profile synchronized` event that sets the profile property\n`neostore.authenticationToken` for the holder; and, for each pass matching one of the holder's\nidentifiers, a `Wallet Installed` event per platform (Apple, Google) the pass is installed on,\ndated at its installation.\n            \nThe Klaviyo listener must be enabled for the tenant.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The Klaviyo profile to synchronise.",
          "content": {
            "application/json": {
              "schema": {
                "description": "The Klaviyo profile to synchronise, as a Klaviyo webhook sends it (snake_case names).",
                "$ref": "#/components/schemas/Profile"
              }
            },
            "text/json": {
              "schema": {
                "description": "The Klaviyo profile to synchronise, as a Klaviyo webhook sends it (snake_case names).",
                "$ref": "#/components/schemas/Profile"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "The Klaviyo profile to synchronise, as a Klaviyo webhook sends it (snake_case names).",
                "$ref": "#/components/schemas/Profile"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Synchronisation accepted."
          },
          "400": {
            "description": "The body is missing or is not valid JSON.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller lacks the `tenant.klaviyo.listener:write` scope, or the Klaviyo listener is not enabled for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 6000 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [
              "tenant.klaviyo.listener:write"
            ]
          },
          {
            "apiKey": [ ]
          }
        ]
      }
    },
    "/api/{tenantId}/webhooks/listeners/secutix/orders": {
      "post": {
        "tags": [
          "Secutix"
        ],
        "summary": "Queue the refresh of the passes of a changed Secutix order.",
        "description": "Returns at once; the passes are updated afterwards. Emits the `Secutix:Order:Updated` event, then\nupdates the existing passes concerned by the change:\n- the pass of `saleMovementId`;\n- the passes of every movement and contact of the order, when `saleMovementId` is omitted or the\n  tenant's `webhook.searchForContactIds` setting is on.\n            \nWith `webhook.updateMetadata` on, each pass also has its data and pass template refreshed from\nSecutix. No pass is created.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The order change notification.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Order change notification, as Secutix sends it.",
                "$ref": "#/components/schemas/OrderChangeRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Order change notification, as Secutix sends it.",
                "$ref": "#/components/schemas/OrderChangeRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Order change notification, as Secutix sends it.",
                "$ref": "#/components/schemas/OrderChangeRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Order change accepted. No body."
          },
          "400": {
            "description": "`orderSecretToken` is empty, or a required field is missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 600 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/webhooks/listeners/sfmc/actions/notify/execute": {
      "post": {
        "tags": [
          "SFMC"
        ],
        "summary": "Executes the Journey Builder notify action.",
        "description": "The body is the token Journey Builder sends for the activity. Sends one notification per matched pass\nand emits an `SFMC:Notify:Executed` event per pass; the response does not wait for delivery to the\ndevices.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Notifications accepted; the body is `{ \"success\": true }`."
          },
          "400": {
            "description": "The arguments cannot be read, the identifiers are unusable, or neither content nor localizedContent carries any text.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated, or the body is not a valid Journey Builder token for this tenant; check the signing key configured for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant."
          },
          "404": {
            "description": "Salesforce Marketing Cloud is not configured for the tenant, or no pass matches the identifiers.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 100000 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            }
          },
          "500": {
            "description": "Unexpected server error."
          }
        }
      }
    },
    "/api/{tenantId}/webhooks/listeners/sfmc/actions/notify/publish": {
      "post": {
        "tags": [
          "SFMC"
        ],
        "summary": "Handles publish handshakes from Journey Builder.",
        "description": "Always acknowledged.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Publish handshake acknowledged; the body is `{ \"success\": true }`."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant."
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/webhooks/listeners/sfmc/actions/pushupdate/execute": {
      "post": {
        "tags": [
          "SFMC"
        ],
        "summary": "Executes the Journey Builder push update action.",
        "description": "The body is the token Journey Builder sends for the activity. Each matched pass gets the data and pass\ntemplate applied and is pushed to the wallets, and an `SFMC:PushUpdate:Executed` event\nis emitted per pass; the response does not wait for the updates.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Pass updates accepted; the body is `{ \"success\": true }`."
          },
          "400": {
            "description": "The arguments cannot be read, the identifiers are unusable, or the pass template is unknown.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated, or the body is not a valid Journey Builder token for this tenant; check the signing key configured for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant."
          },
          "404": {
            "description": "Salesforce Marketing Cloud is not configured for the tenant, or no pass matches the identifiers.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 100000 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            }
          },
          "500": {
            "description": "Unexpected server error."
          }
        }
      }
    },
    "/api/{tenantId}/webhooks/listeners/sfmc/actions/pushupdate/publish": {
      "post": {
        "tags": [
          "SFMC"
        ],
        "summary": "Handles publish handshakes from Journey Builder.",
        "description": "Always acknowledged.",
        "parameters": [
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Publish handshake acknowledged; the body is `{ \"success\": true }`."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The endpoint is not enabled for the tenant."
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/webhooks/listeners/yurplan/{eventId}/order/confirmed": {
      "post": {
        "tags": [
          "Yurplan"
        ],
        "summary": "Create the passes of a confirmed Yurplan order",
        "description": "Emits `Yurplan:Webhook:OrderValidated`, then creates one pass per ticket with the identifier\n`yurplan.ticketId` = `{eventId}|{token}`, on the tenant's default Yurplan pass template. The pass\ncontent comes from Yurplan. A ticket that already has a pass gets no new one, so the call can be replayed\nsafely.",
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "description": "Yurplan identifier of the event the tickets admit to.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The confirmed order.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Envelope of a Yurplan webhook call.",
                "$ref": "#/components/schemas/WebhookRequest_OrderConfirmedData"
              }
            },
            "text/json": {
              "schema": {
                "description": "Envelope of a Yurplan webhook call.",
                "$ref": "#/components/schemas/WebhookRequest_OrderConfirmedData"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Envelope of a Yurplan webhook call.",
                "$ref": "#/components/schemas/WebhookRequest_OrderConfirmedData"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Event emitted, and every ticket of the order has a pass."
          },
          "400": {
            "description": "The body has no `data`, the order no `identifier` or `tickets`, or a\n            ticket no `token` or `identifier`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/webhooks/listeners/yurplan/{eventId}/ticket/canceled": {
      "post": {
        "tags": [
          "Yurplan"
        ],
        "summary": "Handle Yurplan ticket cancellation",
        "description": "Emits `Yurplan:Webhook:TicketCanceled`; the passes whose `yurplan.ticketId` is\n`{eventId}|{token}` are then refreshed from Yurplan, which exposes the ticket's new `status` to the\npass template. The passes stay installed; the pass template decides how a cancelled ticket shows. An\nunknown ticket is accepted and changes nothing.",
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "description": "Yurplan identifier of the event the ticket admits to.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The cancelled ticket.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Envelope of a Yurplan webhook call.",
                "$ref": "#/components/schemas/WebhookRequest_TicketCanceledData"
              }
            },
            "text/json": {
              "schema": {
                "description": "Envelope of a Yurplan webhook call.",
                "$ref": "#/components/schemas/WebhookRequest_TicketCanceledData"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Envelope of a Yurplan webhook call.",
                "$ref": "#/components/schemas/WebhookRequest_TicketCanceledData"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Cancellation accepted."
          },
          "400": {
            "description": "The body has no `data.ticket` with a `token` and an `identifier`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/{tenantId}/webhooks/listeners/yurplan/{eventId}/ticket/checked": {
      "post": {
        "tags": [
          "Yurplan"
        ],
        "summary": "Handle Yurplan ticket check-in",
        "description": "Emits `Yurplan:Webhook:TicketChecked`; the passes whose `yurplan.ticketId` is\n`{eventId}|{token}` are then refreshed from Yurplan, which exposes the ticket's `scanCount` (check-ins\nacross the event's scan lists) and `status` to the pass template. The passes stay installed. An\nunknown ticket is accepted and changes nothing.",
        "parameters": [
          {
            "name": "eventId",
            "in": "path",
            "description": "Yurplan identifier of the event the ticket admits to.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "description": "The checked-in ticket.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Envelope of a Yurplan webhook call.",
                "$ref": "#/components/schemas/WebhookRequest_TicketCheckedData"
              }
            },
            "text/json": {
              "schema": {
                "description": "Envelope of a Yurplan webhook call.",
                "$ref": "#/components/schemas/WebhookRequest_TicketCheckedData"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Envelope of a Yurplan webhook call.",
                "$ref": "#/components/schemas/WebhookRequest_TicketCheckedData"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Check-in accepted."
          },
          "400": {
            "description": "The body has no `data.ticket` with a `token` and an `identifier`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/admin/logs/connect": {
      "get": {
        "tags": [
          "Logs"
        ],
        "summary": "Open a log watcher session",
        "description": "Starts a watcher session and returns the websocket URL to read the logs from.",
        "responses": {
          "200": {
            "description": "Session started; open the websocket immediately.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Where to open the log websocket, and the watcher session that keeps it fed.",
                  "$ref": "#/components/schemas/ConnectResult"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Where to open the log websocket, and the watcher session that keeps it fed.",
                  "$ref": "#/components/schemas/ConnectResult"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Where to open the log websocket, and the watcher session that keeps it fed.",
                  "$ref": "#/components/schemas/ConnectResult"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller does not hold the <c>global:administrator</c> role.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [ ]
          }
        ]
      }
    },
    "/api/admin/logs/ping": {
      "post": {
        "tags": [
          "Logs"
        ],
        "summary": "Keep a log watcher session alive",
        "description": "Extends the session by 45 seconds. Answers 204 whatever the session's state; when logs stop arriving,\ncall `connect` again to start a new session.",
        "requestBody": {
          "description": "The watcher session to keep alive.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to keep a watcher session alive.",
                "$ref": "#/components/schemas/WatchRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to keep a watcher session alive.",
                "$ref": "#/components/schemas/WatchRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to keep a watcher session alive.",
                "$ref": "#/components/schemas/WatchRequest"
              }
            }
          }
        },
        "responses": {
          "204": {
            "description": "Ping accepted."
          },
          "400": {
            "description": "`sessionId` is missing or blank.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller does not hold the <c>global:administrator</c> role.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [ ]
          }
        ]
      }
    },
    "/api/info": {
      "get": {
        "tags": [
          "Global"
        ],
        "summary": "Snapshot of the instance that served the request: hosting, runtime, process and thread pool figures.",
        "description": "Restricted to the Global Administrator role. Each instance answers for itself only. `appService`\nfields can be `null`; `environment.uptime` is a `[d:]h:mm:ss[.FFFFFFF]` duration, and\nmemory figures are in bytes.",
        "responses": {
          "200": {
            "description": "Diagnostics collected successfully."
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "403": {
            "description": "The caller does not hold the <c>global:administrator</c> role.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        },
        "security": [
          {
            "admin-bearer": [ ]
          }
        ]
      }
    },
    "/api/invitations/activate": {
      "post": {
        "tags": [
          "Invitations"
        ],
        "summary": "Activate access and get a just-in-time password-change ticket",
        "description": "Only works for a valid link. Marks the invitee's e-mail as verified and returns the page where they\nchoose a password. A link can be activated once: from then on it resolves to \"used\", which the\nactivation page turns into a sign-in. Once the password is set, the success page leads back to the\nback-office.",
        "requestBody": {
          "description": "The token from the invitation link.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body carrying an invitation link's token.",
                "$ref": "#/components/schemas/InvitationTokenRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body carrying an invitation link's token.",
                "$ref": "#/components/schemas/InvitationTokenRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body carrying an invitation link's token.",
                "$ref": "#/components/schemas/InvitationTokenRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Ticket created.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Where to send the invitee to choose a password.",
                  "$ref": "#/components/schemas/ActivateInvitationResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Where to send the invitee to choose a password.",
                  "$ref": "#/components/schemas/ActivateInvitationResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Where to send the invitee to choose a password.",
                  "$ref": "#/components/schemas/ActivateInvitationResponse"
                }
              }
            }
          },
          "400": {
            "description": "`token` is missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The link is not currently valid.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Too many requests; retry after the delay given in `Retry-After`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/invitations/resend": {
      "post": {
        "tags": [
          "Invitations"
        ],
        "summary": "Send a new link for this invitation",
        "description": "Works for a valid or an expired link (state \"valid\" or \"expired\"): issues a new link, which makes every\nprevious link invalid, and sends the \"Welcome, new link\" e-mail.",
        "requestBody": {
          "description": "The token from the invitation link, valid or expired.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body carrying an invitation link's token.",
                "$ref": "#/components/schemas/InvitationTokenRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body carrying an invitation link's token.",
                "$ref": "#/components/schemas/InvitationTokenRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body carrying an invitation link's token.",
                "$ref": "#/components/schemas/InvitationTokenRequest"
              }
            }
          }
        },
        "responses": {
          "204": {
            "description": "A new link was issued and sent."
          },
          "400": {
            "description": "`token` is missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "409": {
            "description": "The access is already activated, or the link is invalid.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Too many requests; retry after the delay given in `Retry-After`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/invitations/status": {
      "post": {
        "tags": [
          "Invitations"
        ],
        "summary": "Get what this invitation link currently means",
        "description": "Changes nothing, but emits the tenant's `User:InvitationOpened` event whenever the link resolves\nto a user.",
        "requestBody": {
          "description": "The token from the invitation link.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body carrying an invitation link's token.",
                "$ref": "#/components/schemas/InvitationTokenRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body carrying an invitation link's token.",
                "$ref": "#/components/schemas/InvitationTokenRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body carrying an invitation link's token.",
                "$ref": "#/components/schemas/InvitationTokenRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "State resolved; an unusable link is a 200 with `state: invalid`, not an error.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "What an invitation link currently means.",
                  "$ref": "#/components/schemas/InvitationStatusResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "What an invitation link currently means.",
                  "$ref": "#/components/schemas/InvitationStatusResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "What an invitation link currently means.",
                  "$ref": "#/components/schemas/InvitationStatusResponse"
                }
              }
            }
          },
          "400": {
            "description": "`token` is missing.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Too many requests; retry after the delay given in `Retry-After`.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/me": {
      "get": {
        "tags": [
          "Me"
        ],
        "summary": "Get the current user's access state",
        "description": "Called by the back-office right after sign-in. Saves `language` as the user's language when none\nis stored yet, and sends a welcome e-mail the first time a user with no tenant role calls it, whether or\nnot their address is verified. Global administrators do not get the welcome e-mail.",
        "parameters": [
          {
            "name": "language",
            "in": "query",
            "description": "Language the back-office is currently displayed in. Stored when the user has no language yet and it is\none of the back-office languages.",
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Access state returned.",
            "content": {
              "text/plain": {
                "schema": {
                  "description": "Access state of the signed-in back-office user.",
                  "$ref": "#/components/schemas/MeResponse"
                }
              },
              "application/json": {
                "schema": {
                  "description": "Access state of the signed-in back-office user.",
                  "$ref": "#/components/schemas/MeResponse"
                }
              },
              "text/json": {
                "schema": {
                  "description": "Access state of the signed-in back-office user.",
                  "$ref": "#/components/schemas/MeResponse"
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/me/language": {
      "put": {
        "tags": [
          "Me"
        ],
        "summary": "Set the current user's language",
        "description": "Replaces the stored language, which decides the language of the platform e-mails sent to the user.",
        "requestBody": {
          "description": "The back-office language to store for the caller.",
          "content": {
            "application/json": {
              "schema": {
                "description": "Request body to change the signed-in user's back-office language.",
                "$ref": "#/components/schemas/SetLanguageRequest"
              }
            },
            "text/json": {
              "schema": {
                "description": "Request body to change the signed-in user's back-office language.",
                "$ref": "#/components/schemas/SetLanguageRequest"
              }
            },
            "application/*+json": {
              "schema": {
                "description": "Request body to change the signed-in user's back-office language.",
                "$ref": "#/components/schemas/SetLanguageRequest"
              }
            }
          }
        },
        "responses": {
          "204": {
            "description": "Language saved."
          },
          "400": {
            "description": "The language is missing or not one of the back-office languages.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "description": "The caller is not authenticated.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/ping": {
      "get": {
        "tags": [
          "Global"
        ],
        "summary": "Lightweight liveness/readiness probe.",
        "description": "Reports whether the application has fully started and is not stopping.\n            \nIt also returns the host the request was addressed to, and echoes `nonce` when one is supplied.\nCalled on a custom domain, a matching host and nonce confirm that the domain reaches the application.",
        "parameters": [
          {
            "name": "nonce",
            "in": "query",
            "description": "Optional value echoed back, so a caller can prove it reached this application.",
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Application is responding."
          },
          "503": {
            "description": "Application is not ready yet; the problem carries the same fields as the 200 body."
          }
        }
      }
    },
    "/api/swagger/tenantconfiguration/schema": {
      "get": {
        "tags": [
          "TenantConfiguration"
        ],
        "summary": "Gets the tenant configuration reference: one schema component per configuration section, and a markdown\nguide in `info.description`.",
        "description": "The guide groups sections by category, each followed by its hand-written pages, with images inlined as\nbase64 PNG data URIs. The document carries a single placeholder path, `nop`.",
        "responses": {
          "200": {
            "description": "Document returned."
          }
        }
      }
    },
    "/public/{tenantId}/{cacheKey}/{path}": {
      "get": {
        "tags": [
          "Public"
        ],
        "summary": "Downloads one public file of the tenant.",
        "description": "The content type follows the file extension. Responses may be cached by browsers and CDNs: the\n`{cacheKey}` segment can hold any value, and changing it fetches the current version of the file.",
        "parameters": [
          {
            "name": "path",
            "in": "path",
            "description": "Path of the file among the tenant's public files; may contain `/`.",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "tenantId",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "cacheKey",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "File returned."
          },
          "404": {
            "description": "No such public file for the tenant.",
            "content": {
              "text/plain": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              },
              "text/json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          },
          "429": {
            "description": "Over 1200 requests per minute to this endpoint for the tenant (default limit); retry after <c>Retry-After</c>.",
            "headers": {
              "Retry-After": {
                "description": "Seconds to wait before retrying. Sent when the limiter knows it.",
                "schema": {
                  "type": "integer"
                }
              }
            },
            "content": {
              "application/problem+json": {
                "schema": {
                  "oneOf": [
                    {
                      "$ref": "#/components/schemas/ProblemDetails"
                    },
                    {
                      "$ref": "#/components/schemas/HttpValidationProblemDetails"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "APNKeyDefinition": {
        "required": [
          "hasValue",
          "id"
        ],
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Key ID Apple assigned to the key, also found in the file name `AuthKey_{id}.p8`."
          },
          "hasValue": {
            "type": "boolean",
            "description": "Whether the `.p8` private key is set. Without it, no pass update is pushed to devices."
          }
        },
        "additionalProperties": false,
        "description": "Apple Push Notifications key, with the private key material redacted."
      },
      "APNKeyRequest": {
        "required": [
          "id"
        ],
        "type": "object",
        "properties": {
          "id": {
            "minLength": 1,
            "type": "string",
            "description": "Key ID Apple assigned to the key, also found in the file name `AuthKey_{id}.p8`."
          },
          "value": {
            "type": [
              "null",
              "string"
            ],
            "description": "Content of the `.p8` file, PEM block included (`-----BEGIN PRIVATE KEY-----`). Omit or leave\nempty to keep the current key; required the first time Apple Wallet is configured."
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure the Apple Push Notifications key."
      },
      "ActitoConfigurationResponse": {
        "required": [
          "actitoExternalIdentifier",
          "entity",
          "hasApiKey",
          "profileTableName",
          "server",
          "twcExternalIdentifier"
        ],
        "type": "object",
        "properties": {
          "server": {
            "type": "string",
            "description": "Root URL of the Actito API domain the entity lives on.",
            "format": "uri"
          },
          "entity": {
            "minLength": 1,
            "type": "string",
            "description": "Name of the Actito entity the integration works in."
          },
          "profileTableName": {
            "minLength": 1,
            "type": "string",
            "description": "Name of the Actito profile table the holders' profiles are read from."
          },
          "actitoExternalIdentifier": {
            "minLength": 1,
            "type": "string",
            "description": "Attribute of the profile table matched against the pass identifier Neo.Extensions.Actito.Controllers.ActitoConfigurationResponse.TwcExternalIdentifier."
          },
          "twcExternalIdentifier": {
            "minLength": 1,
            "type": "string",
            "description": "Name of the pass identifier matched against Neo.Extensions.Actito.Controllers.ActitoConfigurationResponse.ActitoExternalIdentifier."
          },
          "hasApiKey": {
            "type": "boolean",
            "description": "Whether an API key is stored. When true, a PUT may omit `apiKey` to keep it."
          }
        },
        "additionalProperties": false,
        "description": "The tenant's Actito connection, without the API key."
      },
      "ActitoScriptsDefinition": {
        "required": [
          "profileMapper"
        ],
        "type": "object",
        "properties": {
          "profileMapper": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          }
        },
        "additionalProperties": false,
        "description": "The scripts the Actito integration can be customised with."
      },
      "ActitoWrapper_NewProfile": {
        "type": "object",
        "properties": {
          "eventType": {
            "type": "string",
            "description": "Event type as Actito names it."
          },
          "operation": {
            "type": "string",
            "description": "Operation name as Actito names it. With the route's event type and the profile, identifies the event."
          },
          "data": {
            "description": "The profile the event is about.",
            "$ref": "#/components/schemas/NewProfile"
          }
        },
        "additionalProperties": false,
        "description": "Envelope of an Actito profile webhook."
      },
      "ActivateInvitationResponse": {
        "required": [
          "ticketUrl"
        ],
        "type": "object",
        "properties": {
          "ticketUrl": {
            "minLength": 1,
            "type": "string",
            "description": "Password-change page for the invitee. Valid for 15 minutes; redirect to it immediately."
          }
        },
        "additionalProperties": false,
        "description": "Where to send the invitee to choose a password."
      },
      "AddCustomDomainRequest": {
        "required": [
          "hostname"
        ],
        "type": "object",
        "properties": {
          "hostname": {
            "minLength": 1,
            "type": "string",
            "description": "Hostname to claim, for example `registration.brand.com`. Lowercased server-side."
          }
        },
        "additionalProperties": false,
        "description": "Request body to claim a domain."
      },
      "AddScanRequest": {
        "required": [
          "data",
          "type"
        ],
        "type": "object",
        "properties": {
          "data": {
            "maxLength": 2048,
            "minLength": 3,
            "type": "string",
            "description": "The decoded content, exactly as read. It must equal, character for character, one of the barcode\nvalues rendered on a pass (its Apple or Google barcode message, trimmed)."
          },
          "type": {
            "description": "How `data` was captured. Recorded on the scan event as `scannedType`, in PascalCase (for\nexample `QRCode` for `qrcode`).",
            "$ref": "#/components/schemas/TypeEnum"
          }
        },
        "additionalProperties": false,
        "description": "A value read from a pass by a scanner, a camera or a keyboard."
      },
      "AddScanResponse": {
        "required": [
          "passId"
        ],
        "type": "object",
        "properties": {
          "passId": {
            "type": "string",
            "description": "The pass carrying the scanned value. When several passes carry it, the most recently updated one."
          }
        },
        "additionalProperties": false,
        "description": "The pass the scanned value resolved to."
      },
      "Advisor": {
        "required": [
          "advisorId",
          "displayName"
        ],
        "type": "object",
        "properties": {
          "advisorId": {
            "type": "string",
            "description": "Identifier of the advisor in the tenant's advisor provider."
          },
          "displayName": {
            "type": "string",
            "description": "Advisor name to show to staff and holders."
          }
        },
        "additionalProperties": false,
        "description": "A staff member of a store, as supplied by the advisor provider configured for the tenant."
      },
      "AparteConfigurationResponse": {
        "required": [
          "baseUrl",
          "defaultPassType",
          "hasApiKey",
          "tenant",
          "timeZoneId"
        ],
        "type": "object",
        "properties": {
          "baseUrl": {
            "type": "string",
            "description": "Root URL of the Aparte WalletCrew API, as last saved.",
            "format": "uri"
          },
          "tenant": {
            "minLength": 1,
            "type": "string",
            "description": "Aparte tenant code, sent as the `X-Tenant` header of every call to Aparte."
          },
          "defaultPassType": {
            "minLength": 1,
            "type": "string",
            "description": "Pass template given to a pass created with an `aparte.ticketId` identifier and no pass template."
          },
          "invalidPassType": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template a ticket pass is moved to when Aparte no longer returns its ticket; null when such a\npass keeps its pass template."
          },
          "hasApiKey": {
            "type": "boolean",
            "description": "Whether an API key is stored. When true, a save may omit `apiKey` to keep it."
          },
          "timeZoneId": {
            "minLength": 1,
            "type": "string",
            "description": "Time zone of the venue, e.g. `Europe/Paris`, in which Aparte session dates are read."
          },
          "rateLimit": {
            "description": "Cap on the calls sent to Aparte.",
            "$ref": "#/components/schemas/AparteRateLimitSettings"
          }
        },
        "additionalProperties": false,
        "description": "The stored Aparte configuration of the tenant, without its API key."
      },
      "AparteRateLimitSettings": {
        "type": "object",
        "properties": {
          "throttlingLimit": {
            "maximum": 10000,
            "minimum": 1,
            "type": "integer",
            "description": "Maximum calls per minute sent to Aparte, 1 to 10000 (else 400). Default 500.",
            "format": "int32",
            "default": 500
          }
        },
        "additionalProperties": false,
        "description": "Cap on the calls this tenant sends to Aparte."
      },
      "AparteScriptsDefinition": {
        "required": [
          "ticketMapper"
        ],
        "type": "object",
        "properties": {
          "ticketMapper": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          }
        },
        "additionalProperties": false,
        "description": "The scripts the Aparte integration can be customised with."
      },
      "ApiKeyCreatedResponse": {
        "required": [
          "token"
        ],
        "type": "object",
        "allOf": [
          {
            "$ref": "#/components/schemas/ApiKeyDefinition"
          }
        ],
        "properties": {
          "token": {
            "type": "string",
            "description": "Plaintext API key. Copy and store it immediately — it will not be shown again."
          }
        },
        "additionalProperties": false,
        "description": "Returned once after a successful key creation.\nThe `Token` field contains the plaintext API key and will never be retrievable again."
      },
      "ApiKeyDefinition": {
        "required": [
          "enabled",
          "name",
          "permissions"
        ],
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "Name chosen at creation; identifies the key in every other call and cannot be changed."
          },
          "enabled": {
            "type": "boolean",
            "description": "Whether requests authenticated with this key are accepted. A disabled key is kept but refused."
          },
          "permissions": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Permissions granted to the key, as sent: area wildcards such as `tenant.access:*` are not\nexpanded. Contains `*` when the key has full tenant-administrator access."
          }
        },
        "additionalProperties": false,
        "description": "API key definition returned by list and get endpoints.\nThe key value itself is never returned."
      },
      "AppleNfcSettings": {
        "type": "object",
        "properties": {
          "publicKey": {
            "type": "string",
            "description": "Apple public key used for NFC tap authentication."
          },
          "passTypeIdentifier": {
            "type": "string",
            "description": "Pass type identifier associated with the Apple Wallet pass."
          }
        },
        "additionalProperties": false
      },
      "AppleSignInDefinition": {
        "required": [
          "serviceIdentifier"
        ],
        "type": "object",
        "properties": {
          "serviceIdentifier": {
            "type": "string",
            "description": "Apple Services ID on which \"Sign in with Apple\" is configured. The customer web app starts Sign in\nwith Apple with it. Empty when sign in with Apple is turned off."
          }
        },
        "additionalProperties": false,
        "description": "Sign in with Apple settings."
      },
      "AppleWalletProviderDefinition": {
        "required": [
          "apnKey",
          "pass",
          "teamIdentifier"
        ],
        "type": "object",
        "properties": {
          "teamIdentifier": {
            "type": "string",
            "description": "Apple Developer Team ID that owns the pass type identifier, written into every Apple pass."
          },
          "apnKey": {
            "description": "Key used to push pass updates to devices through the Apple Push Notification service.",
            "$ref": "#/components/schemas/APNKeyDefinition"
          },
          "pass": {
            "description": "Pass type identifier and the certificate Apple passes are signed with.",
            "$ref": "#/components/schemas/PassDefinition"
          },
          "webServiceUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "Web service URL written into every Apple pass generated from now on, which Apple Wallet calls to\nregister devices and fetch updates. Null means the platform's own endpoint,\n`/api/{tenantId}/passes/apple`.",
            "format": "uri"
          }
        },
        "additionalProperties": false,
        "description": "Apple Wallet provider settings."
      },
      "ApplyMovementRequest": {
        "required": [
          "oldValue",
          "value"
        ],
        "type": "object",
        "properties": {
          "oldValue": {
            "type": "number",
            "description": "The sum of the benefit's movements as the caller last read it.",
            "format": "double"
          },
          "value": {
            "type": "number",
            "description": "Signed change to apply, in whole uses. Positive issues or awards, negative redeems or uses.\nCannot be zero; a fractional value is refused with 400.",
            "format": "double"
          },
          "remarks": {
            "maxLength": 500,
            "minLength": 1,
            "type": [
              "null",
              "string"
            ],
            "description": "Operator or integration note about the movement, e.g. the till receipt number. Never shown to the\nholder."
          }
        },
        "additionalProperties": false,
        "description": "Request model to apply a movement (transaction) to a benefit's value."
      },
      "ApplyStampRequest": {
        "required": [
          "oldValue",
          "value"
        ],
        "type": "object",
        "properties": {
          "value": {
            "maximum": 100,
            "minimum": -100,
            "type": "integer",
            "description": "Signed change in stamps. Positive stamps the card, negative corrects it — a double scan is\nundone with `-1`.",
            "format": "int32"
          },
          "oldValue": {
            "type": "integer",
            "description": "The count the caller read before deciding on this movement, from `count` on the board.",
            "format": "int32"
          },
          "remarks": {
            "maxLength": 500,
            "type": [
              "null",
              "string"
            ],
            "description": "Free-text note stored on the movement and sent with the `Pass:StampApplied` event. At most 500 characters, otherwise 400."
          }
        },
        "additionalProperties": false,
        "description": "Request to add stamps to, or correct, a card."
      },
      "ApplyStampResponse": {
        "type": "object",
        "properties": {
          "movementId": {
            "type": "string",
            "description": "Identifier of the movement that was recorded."
          },
          "value": {
            "type": "integer",
            "description": "The signed change that was recorded, always the one that was asked for.",
            "format": "int32"
          },
          "count": {
            "type": "integer",
            "description": "Stamps on the board afterwards, and the `oldValue` for the next call. Already back to 0 when the goal was reached on a `ResetImmediately` card.",
            "format": "int32"
          },
          "target": {
            "type": "integer",
            "description": "Stamps needed to reach the goal.",
            "format": "int32"
          },
          "state": {
            "type": "string",
            "description": "`goalReached` when `count` is at or above `target`, otherwise `collecting`."
          },
          "goalReached": {
            "type": "boolean",
            "description": "Whether this movement reached the goal, even when the board was cleared right after."
          }
        },
        "additionalProperties": false,
        "description": "The outcome of applying a movement."
      },
      "AudienceEvaluationMode": {
        "enum": [
          "snapshot",
          "continuous"
        ],
        "type": "string",
        "description": "Whether a Neo.Runtime.Scheduler.Configuration.FixedDateTrigger acts only on the passes matching at Neo.Runtime.Scheduler.Configuration.FixedDateTrigger.RunAt,\nor also on passes that come to match later."
      },
      "Automation": {
        "required": [
          "id",
          "trigger",
          "type"
        ],
        "type": "object",
        "properties": {
          "id": {
            "minLength": 1,
            "type": "string",
            "description": "Identifier, unique within the tenant, and cannot be changed once created. Letters, digits, `_`\nand `-`, up to 200 characters."
          },
          "displayName": {
            "type": [
              "null",
              "string"
            ],
            "description": "Human-friendly label shown in the admin. Optional, up to 200 characters when set or changed."
          },
          "type": {
            "minLength": 1,
            "type": "string",
            "description": "The task type that runs, e.g. `wallet.pushUpdates`. Must be a type available to the tenant, and\nit decides the shape of Neo.Web.Api.Scheduler.Controllers.Automation.Settings."
          },
          "isEnabled": {
            "type": "boolean",
            "description": "Whether the automation fires. A disabled automation is kept but does not run, and does not prevent\ndeleting the theme it applies. Defaults to `true`: omitted, a new automation is live at once.",
            "default": true
          },
          "trigger": {
            "oneOf": [
              {
                "description": "Fires on a cron schedule.",
                "$ref": "#/components/schemas/AutomationRecurrenceTrigger"
              },
              {
                "$ref": "#/components/schemas/AutomationFixedDateTrigger"
              },
              {
                "$ref": "#/components/schemas/AutomationDateRelativeTrigger"
              },
              {
                "$ref": "#/components/schemas/AutomationEventTrigger"
              }
            ],
            "description": "When the automation fires."
          },
          "settings": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": { },
            "description": "Type-specific configuration — which benefit template to apply, which audience to match. Its shape is decided by\nNeo.Web.Api.Scheduler.Controllers.Automation.Type and validated on write: a key the type does not declare, a value of the wrong type,\na broken constraint, or a pass template, theme or benefit template the tenant does not have is refused\nwith a 400. Omitted, the type's default settings apply."
          },
          "actions": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "What this automation does to each pass it matches — any of `applyBenefitTemplate`, `updateData`,\n`changePassType`, `applyTheme`, `notify`. Derived from Neo.Web.Api.Scheduler.Controllers.Automation.Settings;\nread-only, and ignored on write."
          },
          "tags": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Free-form labels used to filter and group automations in the admin. At most 20 tags of 50 characters;\neach is trimmed, blank ones are dropped and a tag repeated in another casing is kept once."
          },
          "creationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the automation was created with this API, in UTC. Set by the server; ignored on write. `null` when it was not created with this API. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "lastModificationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the automation was last created or updated through this API, in UTC. Set by the server; ignored on write. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          }
        },
        "additionalProperties": false,
        "description": "One automation."
      },
      "AutomationBenefitRedeemedEventSettings": {
        "required": [
          "direction",
          "type"
        ],
        "type": "object",
        "allOf": [
          {
            "$ref": "#/components/schemas/AutomationEventSettings"
          }
        ],
        "properties": {
          "benefitTemplates": {
            "type": "array",
            "items": {
              "description": "One benefit template an Neo.Web.Api.Scheduler.Controllers.AutomationBenefitRedeemedEventSettings watches.",
              "$ref": "#/components/schemas/AutomationBenefitTemplateSelection"
            },
            "description": "The benefit templates to watch. Empty or omitted means every benefit template."
          },
          "options": {
            "description": "Conditions applied to a benefit template that declares none of its own, and to every benefit template when\nNeo.Web.Api.Scheduler.Controllers.AutomationBenefitRedeemedEventSettings.BenefitTemplates is empty.",
            "$ref": "#/components/schemas/AutomationBenefitTemplateSelectionOptions"
          },
          "direction": {
            "description": "Which way the movement has to go: a redemption (negative value), an award (positive value), or either.",
            "$ref": "#/components/schemas/MovementDirection"
          },
          "offset": {
            "description": "Delay after the movement. Omitted means shortly after the movement.",
            "$ref": "#/components/schemas/AutomationTriggerOffset"
          },
          "type": {
            "enum": [
              "Benefit:MovementApplied"
            ],
            "type": "string",
            "description": "Discriminator. Always `Benefit:MovementApplied` for this shape."
          }
        },
        "additionalProperties": false,
        "description": "Reacts to a movement applied to a benefit issued by a benefit template: a redemption, an award or\neither, as Neo.Web.Api.Scheduler.Controllers.AutomationBenefitRedeemedEventSettings.Direction says."
      },
      "AutomationBenefitTemplateSelection": {
        "required": [
          "benefitTemplateId"
        ],
        "type": "object",
        "properties": {
          "benefitTemplateId": {
            "minLength": 1,
            "type": "string",
            "description": "Id of the benefit template whose benefits are watched. May not be blank nor listed twice in\n`benefitTemplates`; either is refused with a 400."
          },
          "options": {
            "description": "Conditions for this benefit template. When omitted, the settings-level\nNeo.Web.Api.Scheduler.Controllers.AutomationBenefitRedeemedEventSettings.Options applies.",
            "$ref": "#/components/schemas/AutomationBenefitTemplateSelectionOptions"
          }
        },
        "additionalProperties": false,
        "description": "One benefit template an Neo.Web.Api.Scheduler.Controllers.AutomationBenefitRedeemedEventSettings watches."
      },
      "AutomationBenefitTemplateSelectionOptions": {
        "type": "object",
        "properties": {
          "whenFullyRedeemed": {
            "type": "boolean",
            "description": "Fire only on the movement that leaves the benefit with nothing left (its total value reaches zero). A\nmulti-use benefit then fires on its last use rather than on its first. Defaults to `false`."
          }
        },
        "additionalProperties": false,
        "description": "Conditions on one watched benefit template, beyond a movement having happened on it."
      },
      "AutomationDateRelativeTrigger": {
        "required": [
          "direction",
          "offset",
          "referenceField",
          "type"
        ],
        "type": "object",
        "allOf": [
          {
            "$ref": "#/components/schemas/AutomationTrigger"
          }
        ],
        "properties": {
          "referenceField": {
            "minLength": 1,
            "type": "string",
            "description": "Name of the pass data field the moment is computed from, e.g. `birthDate`. Must be declared with\ntype `datetime` on at least one pass template, or the write is refused with a 400."
          },
          "direction": {
            "description": "Whether the automation fires before or after the reference field.",
            "$ref": "#/components/schemas/AutomationTriggerDirection"
          },
          "offset": {
            "description": "How far from the reference field the automation fires.",
            "$ref": "#/components/schemas/AutomationTriggerOffset"
          },
          "pinnedTime": {
            "description": "Snaps the computed moment to this time of day, on the date it falls on in the given timezone, rather\nthan keeping the time of day the field carries. Omitted, the computed moment is used as is.",
            "$ref": "#/components/schemas/AutomationPinnedTime"
          },
          "type": {
            "enum": [
              "dateRelative"
            ],
            "type": "string",
            "description": "Discriminator. Always `dateRelative` for this shape."
          }
        },
        "additionalProperties": false,
        "description": "Fires per pass, at a moment computed from one of the pass date fields."
      },
      "AutomationEventSettings": {
        "type": "object",
        "description": "Which pass event an Neo.Web.Api.Scheduler.Controllers.AutomationEventTrigger reacts to. Discriminated by `type`."
      },
      "AutomationEventTrigger": {
        "required": [
          "settings",
          "type"
        ],
        "type": "object",
        "allOf": [
          {
            "$ref": "#/components/schemas/AutomationTrigger"
          }
        ],
        "properties": {
          "settings": {
            "oneOf": [
              {
                "description": "Reacts to a pass being installed on a device.",
                "$ref": "#/components/schemas/AutomationPassInstalledEventSettings"
              },
              {
                "$ref": "#/components/schemas/AutomationBenefitRedeemedEventSettings"
              },
              {
                "$ref": "#/components/schemas/AutomationMetadataChangedEventSettings"
              }
            ],
            "description": "The event to react to, and its conditions."
          },
          "type": {
            "enum": [
              "event"
            ],
            "type": "string",
            "description": "Discriminator. Always `event` for this shape."
          }
        },
        "additionalProperties": false,
        "description": "Fires per pass, when a pass event occurs."
      },
      "AutomationFixedDateTrigger": {
        "required": [
          "runAt",
          "type"
        ],
        "type": "object",
        "allOf": [
          {
            "$ref": "#/components/schemas/AutomationTrigger"
          }
        ],
        "properties": {
          "runAt": {
            "type": "string",
            "description": "The instant the automation fires. A new or changed value must be in the future; an automation that\nalready fired keeps its past `runAt` across edits of its other fields.",
            "format": "date-time"
          },
          "audienceEvaluationMode": {
            "description": "`snapshot` evaluates the audience once, at `runAt`. `continuous` keeps evaluating it\n            afterwards, applying once to each pass that newly matches, for as long as\n            `monitoringPeriod` stays open. Omitted means `snapshot`.",
            "default": "snapshot",
            "$ref": "#/components/schemas/AudienceEvaluationMode"
          },
          "type": {
            "enum": [
              "fixedDate"
            ],
            "type": "string",
            "description": "Discriminator. Always `fixedDate` for this shape."
          }
        },
        "additionalProperties": false,
        "description": "Fires once, at a given instant."
      },
      "AutomationMetadataChangedEventSettings": {
        "required": [
          "key",
          "type"
        ],
        "type": "object",
        "allOf": [
          {
            "$ref": "#/components/schemas/AutomationEventSettings"
          }
        ],
        "properties": {
          "key": {
            "minLength": 1,
            "type": "string",
            "description": "Metadata key to watch, as declared on the pass templates."
          },
          "offset": {
            "description": "Delay after the change. Omitted means in the same update as the change.",
            "$ref": "#/components/schemas/AutomationTriggerOffset"
          },
          "type": {
            "enum": [
              "Pass:MetadataChanged"
            ],
            "type": "string",
            "description": "Discriminator. Always `Pass:MetadataChanged` for this shape."
          }
        },
        "additionalProperties": false,
        "description": "Reacts to the value of one metadata key of a pass changing: a value that appears, changes or disappears."
      },
      "AutomationMonitoringPeriod": {
        "type": "object",
        "description": "When an Neo.Web.Api.Scheduler.Controllers.AutomationTrigger stops - re-evaluating its audience, or firing at all."
      },
      "AutomationOffsetUnit": {
        "enum": [
          "minutes",
          "hours",
          "days",
          "weeks"
        ],
        "type": "string",
        "description": "The unit an offset is expressed in."
      },
      "AutomationPassInstalledEventSettings": {
        "required": [
          "condition",
          "type"
        ],
        "type": "object",
        "allOf": [
          {
            "description": "Which pass event an Neo.Web.Api.Scheduler.Controllers.AutomationEventTrigger reacts to. Discriminated by `type`.",
            "$ref": "#/components/schemas/AutomationEventSettings"
          }
        ],
        "properties": {
          "condition": {
            "description": "Whether the trigger fires only on the first install or on every install.",
            "$ref": "#/components/schemas/PassInstalledCondition"
          },
          "offset": {
            "description": "Delay after the install. Omitted means shortly after the install.",
            "$ref": "#/components/schemas/AutomationTriggerOffset"
          },
          "type": {
            "enum": [
              "Pass:Installed"
            ],
            "type": "string",
            "description": "Discriminator. Always `Pass:Installed` for this shape."
          }
        },
        "additionalProperties": false,
        "description": "Reacts to a pass being installed on a device."
      },
      "AutomationPinnedTime": {
        "required": [
          "hour",
          "timezone"
        ],
        "type": "object",
        "properties": {
          "hour": {
            "minLength": 1,
            "type": "string",
            "description": "Wall-clock time of day, 24-hour `HH:mm` (`09:30`). Refused with a 400 in any other format."
          },
          "timezone": {
            "minLength": 1,
            "type": "string",
            "description": "IANA timezone id Neo.Web.Api.Scheduler.Controllers.AutomationPinnedTime.Hour is read in, e.g. `Europe/Paris`. An unknown id is refused with a 400."
          }
        },
        "additionalProperties": false,
        "description": "Pins a computed moment to a wall-clock time in a timezone."
      },
      "AutomationRecurrenceTrigger": {
        "required": [
          "scheduleExpression",
          "type"
        ],
        "type": "object",
        "allOf": [
          {
            "description": "When an automation fires. Discriminated by `type`.",
            "$ref": "#/components/schemas/AutomationTrigger"
          }
        ],
        "properties": {
          "scheduleExpression": {
            "minLength": 1,
            "type": "string",
            "description": "Six-field cron expression (seconds first), evaluated in UTC — `0 0 9 * * *` is every day at 09:00\nUTC. An optional trailing four-digit year limits it to that year. Rejected when it does not parse. A\nnew or changed expression is also rejected when two of its occurrences fall less than five minutes\napart."
          },
          "type": {
            "enum": [
              "recurrence"
            ],
            "type": "string",
            "description": "Discriminator. Always `recurrence` for this shape."
          }
        },
        "additionalProperties": false,
        "description": "Fires on a cron schedule."
      },
      "AutomationSortModel": {
        "type": "object",
        "properties": {
          "field": {
            "type": "string",
            "description": "`startDate`, `taskId`, `taskType`, `duration` or `retryIndex`, case-sensitive. Any\n            other value is refused with a 400."
          },
          "direction": {
            "description": "`ASC` or `DESC`.",
            "$ref": "#/components/schemas/AutomationSortModelDirection"
          }
        },
        "additionalProperties": false,
        "description": "One sort key of an execution list, passed as `sortBy[i].field` and `sortBy[i].direction`.\nKeys apply in order; ties are then broken by execution id, descending."
      },
      "AutomationSortModelDirection": {
        "enum": [
          0,
          1
        ],
        "type": "integer",
        "description": "Sort direction of one Neo.Web.Api.Scheduler.Controllers.AutomationSortModel.",
        "format": "int32"
      },
      "AutomationTrigger": {
        "type": "object",
        "properties": {
          "monitoringPeriod": {
            "type": "null",
            "oneOf": [
              {
                "description": "Never expires on its own; the automation stops when it is disabled or deleted.",
                "$ref": "#/components/schemas/AutomationUntilStoppedMonitoringPeriod"
              },
              {
                "$ref": "#/components/schemas/AutomationUntilDateMonitoringPeriod"
              },
              {
                "$ref": "#/components/schemas/AutomationUntilBenefitTemplateEndMonitoringPeriod"
              }
            ],
            "description": "When the automation stops. Omitted means it runs until it is disabled or deleted. Required on a\nNeo.Web.Api.Scheduler.Controllers.AutomationFixedDateTrigger whose `audienceEvaluationMode` is `continuous`,\nand refused on one whose mode is `snapshot` - a one-shot run has nothing to end."
          }
        },
        "description": "When an automation fires. Discriminated by `type`."
      },
      "AutomationTriggerDirection": {
        "enum": [
          "before",
          "after"
        ],
        "type": "string",
        "description": "Which side of the reference field a Neo.Web.Api.Scheduler.Controllers.AutomationDateRelativeTrigger fires on."
      },
      "AutomationTriggerOffset": {
        "required": [
          "unit",
          "value"
        ],
        "type": "object",
        "properties": {
          "value": {
            "maximum": 2147483647,
            "minimum": 0,
            "type": "integer",
            "description": "How many Neo.Web.Api.Scheduler.Controllers.AutomationTriggerOffset.Units. Must not be negative - the direction carries the sign.",
            "format": "int32"
          },
          "unit": {
            "description": "The unit Neo.Web.Api.Scheduler.Controllers.AutomationTriggerOffset.Value counts.",
            "$ref": "#/components/schemas/AutomationOffsetUnit"
          }
        },
        "additionalProperties": false,
        "description": "A duration expressed in a unit an operator thinks in."
      },
      "AutomationUntilBenefitTemplateEndMonitoringPeriod": {
        "required": [
          "mode"
        ],
        "type": "object",
        "allOf": [
          {
            "$ref": "#/components/schemas/AutomationMonitoringPeriod"
          }
        ],
        "properties": {
          "mode": {
            "enum": [
              "untilBenefitTemplateEnd"
            ],
            "type": "string",
            "description": "Discriminator. Always `untilBenefitTemplateEnd` for this shape."
          }
        },
        "additionalProperties": false,
        "description": "Stops when the referenced benefit template's own validity ends. Only for tasks that grant a benefit\ntemplate (`settings.benefitTemplateId`), and only when that benefit template has a fixed end date;\notherwise the write is refused with a 400."
      },
      "AutomationUntilDateMonitoringPeriod": {
        "required": [
          "endDate",
          "mode"
        ],
        "type": "object",
        "allOf": [
          {
            "$ref": "#/components/schemas/AutomationMonitoringPeriod"
          }
        ],
        "properties": {
          "endDate": {
            "type": "string",
            "description": "The instant the automation stops. On create it must be in the future; on a `fixedDate` trigger\nit must also be later than `runAt`. Refused with a 400 otherwise.",
            "format": "date-time"
          },
          "mode": {
            "enum": [
              "untilDate"
            ],
            "type": "string",
            "description": "Discriminator. Always `untilDate` for this shape."
          }
        },
        "additionalProperties": false,
        "description": "Stops once Neo.Web.Api.Scheduler.Controllers.AutomationUntilDateMonitoringPeriod.EndDate is reached."
      },
      "AutomationUntilStoppedMonitoringPeriod": {
        "required": [
          "mode"
        ],
        "type": "object",
        "allOf": [
          {
            "description": "When an Neo.Web.Api.Scheduler.Controllers.AutomationTrigger stops - re-evaluating its audience, or firing at all.",
            "$ref": "#/components/schemas/AutomationMonitoringPeriod"
          }
        ],
        "properties": {
          "mode": {
            "enum": [
              "untilStopped"
            ],
            "type": "string",
            "description": "Discriminator. Always `untilStopped` for this shape."
          }
        },
        "additionalProperties": false,
        "description": "Never expires on its own; the automation stops when it is disabled or deleted."
      },
      "BarcodeType": {
        "enum": [
          "PDF417",
          "UPCA",
          "UPCE",
          "CODE39",
          "CODE93",
          "CODE128",
          "ITF14",
          "EAN13",
          "EAN8",
          "QRCODE"
        ],
        "type": "string",
        "description": "Barcode symbology to render. In the URL the name is matched case-insensitively."
      },
      "Benefit": {
        "required": [
          "benefitId"
        ],
        "type": "object",
        "allOf": [
          {
            "description": "A benefit as read back: what the holder gets, its dates, its balance and its current status.",
            "$ref": "#/components/schemas/BenefitBase"
          }
        ],
        "properties": {
          "benefitId": {
            "type": "string",
            "description": "Unique identifier of the benefit (unique across all passes within the tenant)."
          },
          "passType": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of the standalone wallet pass linked to this benefit. Null when there is none, and\nfor a caller without `tenant.pass:read`."
          },
          "linkedPassId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass ID of the standalone wallet pass generated for this benefit. Null when the pass has not been created yet."
          }
        },
        "additionalProperties": false,
        "description": "Represents a persisted benefit with a required unique identifier."
      },
      "BenefitAppearance": {
        "type": "object",
        "properties": {
          "images": {
            "type": "array",
            "items": {
              "description": "A benefit image and the slot it fills.",
              "$ref": "#/components/schemas/BenefitImage"
            },
            "description": "The images, keyed by the slot each one fills. At most one entry per slot."
          }
        },
        "additionalProperties": false,
        "description": "The images a benefit carries, at most one per slot."
      },
      "BenefitAppearanceRequest": {
        "type": "object",
        "properties": {
          "images": {
            "type": "array",
            "items": {
              "description": "A benefit image and the slot it fills.",
              "$ref": "#/components/schemas/BenefitImage"
            },
            "description": "The images, at most one per slot. Each URL is a web address the holder's browser and the wallet\nrenderers can fetch, or a benefit template image path exactly as a read with the\n`tenant.pass:read` scope returns it."
          },
          "mainImageUrl": {
            "description": "Deprecated. The Neo.Runtime.Benefit.Data.BenefitImageSlot.Main image; use Neo.Web.Api.Benefit.Controllers.BenefitPassController.BenefitAppearanceRequest.Images.",
            "$ref": "#/components/schemas/LocalizedString"
          },
          "thumbnailUrl": {
            "description": "Deprecated. The Neo.Runtime.Benefit.Data.BenefitImageSlot.Thumbnail image; use Neo.Web.Api.Benefit.Controllers.BenefitPassController.BenefitAppearanceRequest.Images.",
            "$ref": "#/components/schemas/LocalizedString"
          }
        },
        "additionalProperties": false,
        "description": "The images on an incoming benefit."
      },
      "BenefitBase": {
        "required": [
          "category",
          "status",
          "type"
        ],
        "type": "object",
        "properties": {
          "priority": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Rank of the benefit among the others on the same pass. Higher comes first; a benefit with no\npriority comes after every benefit with one.",
            "format": "int32"
          },
          "origin": {
            "description": "Where the benefit came from: a benefit template (`generator``benefitTemplate`,\n`processId` the benefit template id) or the integration that pushed it.",
            "$ref": "#/components/schemas/BenefitOrigin"
          },
          "type": {
            "description": "How the benefit is consumed: `OneTime` is redeemed once, `MultiUse` counts down a number\nof uses, `Unlimited` is never used up.",
            "$ref": "#/components/schemas/BenefitType"
          },
          "category": {
            "description": "What the benefit gives the holder, used to group and label it. `Other` for a benefit stored\nwithout one.",
            "$ref": "#/components/schemas/BenefitCategory"
          },
          "tags": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Labels for segmenting and reporting. Never shown to the holder; omitted for a caller without\n`tenant.pass:read`."
          },
          "content": {
            "description": "The title and description the holder reads.",
            "$ref": "#/components/schemas/BenefitContent"
          },
          "appearance": {
            "description": "The benefit's images, at most one per slot.",
            "$ref": "#/components/schemas/BenefitAppearance"
          },
          "links": {
            "type": [
              "null",
              "object"
            ],
            "properties": {
              "LegalInformation": {
                "description": "A single link with a localized title and a target URI.",
                "$ref": "#/components/schemas/BenefitLink"
              },
              "CallToAction": {
                "description": "A single link with a localized title and a target URI.",
                "$ref": "#/components/schemas/BenefitLink"
              },
              "TermsAndConditions": {
                "description": "A single link with a localized title and a target URI.",
                "$ref": "#/components/schemas/BenefitLink"
              },
              "PrivacyPolicy": {
                "description": "A single link with a localized title and a target URI.",
                "$ref": "#/components/schemas/BenefitLink"
              },
              "HowToUse": {
                "description": "A single link with a localized title and a target URI.",
                "$ref": "#/components/schemas/BenefitLink"
              },
              "Website": {
                "description": "A single link with a localized title and a target URI.",
                "$ref": "#/components/schemas/BenefitLink"
              },
              "Other": {
                "description": "A single link with a localized title and a target URI.",
                "$ref": "#/components/schemas/BenefitLink"
              }
            },
            "additionalProperties": false,
            "description": "Links shown with the benefit on the benefits page, keyed by purpose."
          },
          "data": {
            "description": "The benefit's balance, its movement history and its provider payload.",
            "$ref": "#/components/schemas/BenefitData"
          },
          "activationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit becomes redeemable. Null means straight away. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "deactivationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit stops being redeemable. Null means it never expires. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "deletionDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit is removed from the pass. Null means never, and for a caller without\n`tenant.pass:read`. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "behavior": {
            "description": "The allowance a `MultiUse` benefit counts down from, and where the benefit is surfaced.",
            "$ref": "#/components/schemas/BenefitBehavior"
          },
          "code": {
            "description": "The code staff scan or type to redeem the benefit, with how it is rendered. Null for a benefit\nwith no code.",
            "$ref": "#/components/schemas/BenefitCode"
          },
          "creationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit was issued. Set by the server; ignored on write. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "lastModificationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit last changed: an update, a movement, or a refresh from its benefit template. Set by\nthe server. Null for a caller without `tenant.pass:read`. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "status": {
            "description": "What this benefit is doing right now.",
            "$ref": "#/components/schemas/BenefitStatus"
          }
        },
        "additionalProperties": false,
        "description": "A benefit as read back: what the holder gets, its dates, its balance and its current status."
      },
      "BenefitBehavior": {
        "type": "object",
        "properties": {
          "target": {
            "type": [
              "null",
              "number"
            ],
            "description": "The number of uses a `MultiUse` benefit started with - the \"5\" in \"3 of 5 left\", where 3 is\n`data.value`. Null when there is no allowance to count down from.",
            "format": "double"
          },
          "mode": {
            "type": "array",
            "items": {
              "description": "Where a benefit is shown and what each surface does with it.",
              "$ref": "#/components/schemas/BenefitBehaviorMode"
            },
            "description": "Where the benefit is surfaced and what each surface does with it, one entry per behaviour."
          }
        },
        "additionalProperties": false,
        "description": "Behavioral configuration for a benefit."
      },
      "BenefitBehaviorMode": {
        "enum": [
          "None",
          "ShowOnBenefitListPage",
          "ShowOnPassScanner",
          "RedeemOnScan",
          "UseMainImageAsWalletImage",
          "AddDescriptionAsBackField"
        ],
        "type": "string",
        "description": "Where a benefit is shown and what each surface does with it."
      },
      "BenefitBehaviorRequest": {
        "type": "object",
        "properties": {
          "target": {
            "type": [
              "null",
              "number"
            ],
            "description": "The number of uses a `MultiUse` benefit starts with: it seeds the balance of a benefit created\nwithout movements, and caps what a later credit can give back.",
            "format": "double"
          },
          "mode": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Where a benefit is shown and what each surface does with it.",
              "$ref": "#/components/schemas/BenefitBehaviorMode"
            },
            "description": "Where the benefit is surfaced and what each surface does with it. Omit for the default."
          },
          "autoRedeem": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Deprecated. Equivalent to including Neo.Runtime.Benefit.Data.BenefitBehaviorMode.RedeemOnScan in Neo.Web.Api.Benefit.Controllers.BenefitPassController.BenefitBehaviorRequest.Mode."
          }
        },
        "additionalProperties": false,
        "description": "Behavioral configuration on an incoming benefit."
      },
      "BenefitCategory": {
        "enum": [
          "Other",
          "Discount",
          "FreeProduct",
          "Service",
          "Access",
          "GiftCard"
        ],
        "type": "string",
        "description": "What a benefit gives the holder, used to group and label it on the benefits page and in reports."
      },
      "BenefitCode": {
        "type": "object",
        "properties": {
          "value": {
            "type": [
              "null",
              "string"
            ],
            "description": "The code itself, as encoded in the barcode and shown under it."
          },
          "format": {
            "description": "How the code is rendered: a barcode symbology, or `raw` for text only. `ean13` needs\n12 or 13 digits.",
            "$ref": "#/components/schemas/BenefitCodeFormat"
          }
        },
        "additionalProperties": false,
        "description": "Barcode or reference code associated with a benefit, together with its display format."
      },
      "BenefitCodeFormat": {
        "enum": [
          "Ean13",
          "Code128",
          "QrCode",
          "Pdf417",
          "Aztec",
          "DataMatrix",
          "Code39",
          "Raw"
        ],
        "type": "string",
        "description": "How a benefit's code is rendered to the holder, and so what the till or the Pass Scanner scans."
      },
      "BenefitContent": {
        "type": "object",
        "properties": {
          "title": {
            "description": "The benefit's name as the holder sees it, on the benefits page and as a wallet pass field. A benefit\nwithout one is shown as \"Untitled benefit\".",
            "$ref": "#/components/schemas/LocalizedString"
          },
          "description": {
            "description": "What the benefit gives and how to use it, shown on the benefits page and, when the behaviour asks\nfor it, on the back of the wallet pass.",
            "$ref": "#/components/schemas/LocalizedString"
          }
        },
        "additionalProperties": false,
        "description": "The holder-facing texts of a benefit."
      },
      "BenefitData": {
        "type": "object",
        "properties": {
          "value": {
            "type": [
              "null",
              "number"
            ],
            "description": "The uses left: the sum of every movement. A `OneTime` or `MultiUse` benefit at 0 or below\nis `Used`; for `Unlimited` it is a tally of what was taken, not a stock.",
            "format": "double"
          },
          "movements": {
            "type": "array",
            "items": {
              "description": "Represents a single movement or transaction affecting a benefit's value.",
              "$ref": "#/components/schemas/BenefitMovement"
            },
            "description": "Every change to the balance, oldest first. Append-only: a movement is never edited or deleted."
          },
          "content": {
            "maxLength": 500,
            "minLength": 1,
            "type": [
              "null",
              "string"
            ],
            "description": "Free text returned as sent, for a pass template or an integration to read."
          }
        },
        "additionalProperties": false,
        "description": "Runtime state and payload associated with a benefit."
      },
      "BenefitExportTokenResponse": {
        "type": "object",
        "properties": {
          "downloadUrl": {
            "type": "string",
            "description": "Absolute URL of `GET export/download`, valid 30 minutes. It carries its own credential, so a\nbrowser can open it directly without an Authorization header; keep it private."
          }
        },
        "additionalProperties": false,
        "description": "The link the Excel export is downloaded from."
      },
      "BenefitImage": {
        "required": [
          "slot",
          "url"
        ],
        "type": "object",
        "properties": {
          "slot": {
            "description": "Where the image is used: `main` for the headline visual (and the pass artwork when the\nbehaviour asks for it), `thumbnail` for compact lists.",
            "$ref": "#/components/schemas/BenefitImageSlot"
          },
          "url": {
            "description": "The image URL, localized.",
            "$ref": "#/components/schemas/LocalizedString"
          }
        },
        "additionalProperties": false,
        "description": "A benefit image and the slot it fills."
      },
      "BenefitImageSlot": {
        "enum": [
          "Main",
          "Thumbnail"
        ],
        "type": "string",
        "description": "The image slots a benefit can fill."
      },
      "BenefitLink": {
        "required": [
          "link"
        ],
        "type": "object",
        "properties": {
          "title": {
            "description": "The button label shown on the benefits page.",
            "$ref": "#/components/schemas/LocalizedString"
          },
          "link": {
            "type": "string",
            "description": "The address the button opens: an absolute `https` URI.",
            "format": "uri"
          }
        },
        "additionalProperties": false,
        "description": "A single link with a localized title and a target URI."
      },
      "BenefitListCardTranslations": {
        "type": "object",
        "properties": {
          "showCode": {
            "type": [
              "null",
              "string"
            ],
            "description": "Label of the action revealing the redemption code."
          },
          "seeDetails": {
            "type": [
              "null",
              "string"
            ],
            "description": "Label of the action opening the benefit's details."
          },
          "hide": {
            "type": [
              "null",
              "string"
            ],
            "description": "Label of the action closing the opened card."
          },
          "used": {
            "type": [
              "null",
              "string"
            ],
            "description": "Badge on a benefit that has been used up."
          },
          "expired": {
            "type": [
              "null",
              "string"
            ],
            "description": "Badge on a benefit whose validity has passed."
          },
          "remaining": {
            "type": [
              "null",
              "string"
            ],
            "description": "Remaining allowance, for two or more. Carries `{value}` and `{target}` placeholders."
          },
          "remaining_one": {
            "type": [
              "null",
              "string"
            ],
            "description": "Remaining allowance, for exactly one."
          },
          "remainingLabel": {
            "type": [
              "null",
              "string"
            ],
            "description": "Screen-reader wording of the remaining allowance."
          },
          "progress": {
            "type": [
              "null",
              "string"
            ],
            "description": "Progress towards a reward. Carries `{value}` and `{target}` placeholders."
          },
          "progressLabel": {
            "type": [
              "null",
              "string"
            ],
            "description": "Screen-reader wording of the progress."
          },
          "history": {
            "type": [
              "null",
              "string"
            ],
            "description": "Heading above the list of past redemptions."
          },
          "usedOn": {
            "type": [
              "null",
              "string"
            ],
            "description": "One redemption in that list. Carries a `{date}` placeholder."
          },
          "legal": {
            "type": [
              "null",
              "string"
            ],
            "description": "Label of the link to the benefit's terms."
          },
          "dateRange": {
            "type": [
              "null",
              "string"
            ],
            "description": "Validity of a benefit that both starts and ends. Carries `{from}` and `{to}` placeholders."
          },
          "dateUntil": {
            "type": [
              "null",
              "string"
            ],
            "description": "Validity of a benefit that only ends. Carries a `{to}` placeholder."
          },
          "dateFrom": {
            "type": [
              "null",
              "string"
            ],
            "description": "Validity of a benefit that only starts. Carries a `{from}` placeholder."
          },
          "dateOn": {
            "type": [
              "null",
              "string"
            ],
            "description": "Validity of a benefit good for a single day. Carries a `{from}` placeholder."
          }
        },
        "additionalProperties": false,
        "description": "Strings on the card of one benefit on a `benefitList` page."
      },
      "BenefitListCodeTranslations": {
        "type": "object",
        "properties": {
          "label": {
            "type": [
              "null",
              "string"
            ],
            "description": "Instruction above the code."
          },
          "howTo": {
            "type": [
              "null",
              "string"
            ],
            "description": "Explanation of how the code is redeemed."
          }
        },
        "additionalProperties": false,
        "description": "Strings around the redemption code of a benefit."
      },
      "BenefitListEmptyTranslations": {
        "type": "object",
        "properties": {
          "title": {
            "type": [
              "null",
              "string"
            ],
            "description": "Headline of the empty state."
          },
          "content": {
            "type": [
              "null",
              "string"
            ],
            "description": "Text under the empty-state headline."
          }
        },
        "additionalProperties": false,
        "description": "Strings shown on a `benefitList` page when the pass carries no benefit."
      },
      "BenefitListLayoutTranslations": {
        "type": "object",
        "properties": {
          "title": {
            "type": [
              "null",
              "string"
            ],
            "description": "Headline of the page."
          },
          "subTitle": {
            "type": [
              "null",
              "string"
            ],
            "description": "Text under the headline. Hidden entirely when empty."
          },
          "sections": {
            "description": "Headings of the three groups benefits are listed in.",
            "$ref": "#/components/schemas/BenefitListSectionsTranslations"
          },
          "card": {
            "description": "Strings on the card of one benefit.",
            "$ref": "#/components/schemas/BenefitListCardTranslations"
          },
          "code": {
            "description": "Strings around the code the holder shows to redeem a benefit.",
            "$ref": "#/components/schemas/BenefitListCodeTranslations"
          },
          "wallet": {
            "description": "Strings of the card adding every eligible benefit to the wallet at once.",
            "$ref": "#/components/schemas/BenefitListWalletTranslations"
          },
          "empty": {
            "description": "Strings shown when the pass carries no benefit at all.",
            "$ref": "#/components/schemas/BenefitListEmptyTranslations"
          }
        },
        "additionalProperties": false,
        "description": "Strings of a `benefitList` page, by area of the page."
      },
      "BenefitListPageTranslations": {
        "type": "object",
        "properties": {
          "layout": {
            "description": "The strings of the page itself.",
            "$ref": "#/components/schemas/BenefitListLayoutTranslations"
          }
        },
        "additionalProperties": false,
        "description": "Strings shown on a `benefitList` page."
      },
      "BenefitListSectionsTranslations": {
        "type": "object",
        "properties": {
          "available": {
            "type": [
              "null",
              "string"
            ],
            "description": "Heading above the benefits the holder can use now."
          },
          "upcoming": {
            "type": [
              "null",
              "string"
            ],
            "description": "Heading above the benefits that have not started yet."
          },
          "past": {
            "type": [
              "null",
              "string"
            ],
            "description": "Heading above the benefits that have expired or been used up."
          },
          "pastCount": {
            "type": [
              "null",
              "string"
            ],
            "description": "Counter next to the past heading, for two or more. Carries a `{count}` placeholder."
          },
          "pastCount_one": {
            "type": [
              "null",
              "string"
            ],
            "description": "Counter next to the past heading, for exactly one."
          }
        },
        "additionalProperties": false,
        "description": "Headings of the three groups a `benefitList` page lists benefits in."
      },
      "BenefitListWalletTranslations": {
        "type": "object",
        "properties": {
          "bulkTitle": {
            "type": [
              "null",
              "string"
            ],
            "description": "Headline of the card, for two or more. Carries a `{count}` placeholder."
          },
          "bulkTitle_one": {
            "type": [
              "null",
              "string"
            ],
            "description": "Headline of the card, for exactly one."
          },
          "bulkHint": {
            "type": [
              "null",
              "string"
            ],
            "description": "Text under the headline of the card."
          }
        },
        "additionalProperties": false,
        "description": "Strings of the add-everything card on a `benefitList` page."
      },
      "BenefitMovement": {
        "required": [
          "date",
          "movementId",
          "value"
        ],
        "type": "object",
        "properties": {
          "movementId": {
            "type": "string",
            "description": "Identifier of the movement within the benefit. Replaced by a new one on POST."
          },
          "date": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the movement happened. Stored as sent, so an integration can replay its own history. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "value": {
            "type": "number",
            "description": "The change to the balance: positive issues or credits uses, negative redeems them.",
            "format": "double"
          },
          "remarks": {
            "maxLength": 500,
            "minLength": 1,
            "type": [
              "null",
              "string"
            ],
            "description": "Operator or integration note about the movement, e.g. the till receipt number. Never shown to\nthe holder; omitted for a caller without `tenant.pass:read`."
          }
        },
        "additionalProperties": false,
        "description": "Represents a single movement or transaction affecting a benefit's value."
      },
      "BenefitMovementSummary": {
        "type": "object",
        "properties": {
          "movementId": {
            "type": "string",
            "description": "Identifier of the movement within the benefit."
          },
          "date": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the movement happened. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "value": {
            "type": "number",
            "description": "The change to the balance: positive issues or credits uses, negative redeems them.",
            "format": "double"
          },
          "remarks": {
            "type": [
              "null",
              "string"
            ],
            "description": "Operator or integration note about the movement, if any."
          }
        },
        "additionalProperties": false,
        "description": "Compact summary of a single benefit movement (transaction)."
      },
      "BenefitOrigin": {
        "type": "object",
        "properties": {
          "externalId": {
            "maxLength": 100,
            "minLength": 1,
            "type": [
              "null",
              "string"
            ],
            "description": "Unique external identifier for this benefit within the tenant."
          },
          "generator": {
            "maxLength": 100,
            "minLength": 1,
            "type": [
              "null",
              "string"
            ],
            "description": "Name of the partner or upstream system that generated the benefit, e.g. `salesforce`.\n`benefitTemplate` marks a benefit issued from a benefit template."
          },
          "processId": {
            "maxLength": 100,
            "minLength": 1,
            "type": [
              "null",
              "string"
            ],
            "description": "Identifier of the upstream process or batch job that created this benefit (e.g. `campaign3`)."
          }
        },
        "additionalProperties": false,
        "description": "Describes the origin of a benefit in an external/partner system."
      },
      "BenefitOriginSummary": {
        "required": [
          "count",
          "processId"
        ],
        "type": "object",
        "properties": {
          "processId": {
            "type": "string",
            "description": "The origin process identifier (e.g. benefit template id or external job id)."
          },
          "count": {
            "type": "integer",
            "description": "Number of benefits with this processId, across all passes in the tenant, not yet past their deletion date.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "Live benefit count for a given origin process identifier."
      },
      "BenefitRequestBase": {
        "type": "object",
        "properties": {
          "priority": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Rank of the benefit among the others on the same pass. Higher comes first; a benefit with no\npriority comes after every benefit with one.",
            "format": "int32"
          },
          "origin": {
            "description": "Where the benefit comes from in the caller's system, and the key a POST upserts on.",
            "$ref": "#/components/schemas/BenefitOrigin"
          },
          "tags": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Labels for segmenting and reporting. Never shown to the holder."
          },
          "content": {
            "description": "The title and description the holder reads. Omitted on an update, the current content is kept.",
            "$ref": "#/components/schemas/BenefitContent"
          },
          "appearance": {
            "description": "The images the benefit carries. Omitted on an update, the current images are kept.",
            "$ref": "#/components/schemas/BenefitAppearanceRequest"
          },
          "links": {
            "type": [
              "null",
              "object"
            ],
            "properties": {
              "LegalInformation": {
                "description": "A single link with a localized title and a target URI.",
                "$ref": "#/components/schemas/BenefitLink"
              },
              "CallToAction": {
                "description": "A single link with a localized title and a target URI.",
                "$ref": "#/components/schemas/BenefitLink"
              },
              "TermsAndConditions": {
                "description": "A single link with a localized title and a target URI.",
                "$ref": "#/components/schemas/BenefitLink"
              },
              "PrivacyPolicy": {
                "description": "A single link with a localized title and a target URI.",
                "$ref": "#/components/schemas/BenefitLink"
              },
              "HowToUse": {
                "description": "A single link with a localized title and a target URI.",
                "$ref": "#/components/schemas/BenefitLink"
              },
              "Website": {
                "description": "A single link with a localized title and a target URI.",
                "$ref": "#/components/schemas/BenefitLink"
              },
              "Other": {
                "description": "A single link with a localized title and a target URI.",
                "$ref": "#/components/schemas/BenefitLink"
              }
            },
            "additionalProperties": false,
            "description": "Links shown with the benefit on the benefits page, keyed by purpose. Omitted on an update, the\ncurrent links are kept."
          },
          "data": {
            "description": "The benefit's opening movements and its provider payload.",
            "$ref": "#/components/schemas/BenefitData"
          },
          "activationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit becomes redeemable. Omitted on create, straight away; omitted on an update, the\ncurrent date is kept. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "deactivationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit stops being redeemable. Omitted on create, never; omitted on an update, the current\ndate is kept. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "deletionDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit is removed from the pass. Omitted on create, never. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "behavior": {
            "description": "The allowance a `MultiUse` benefit counts down from, and where the benefit is surfaced.\nOmitted on an update, the current behaviour is kept.",
            "$ref": "#/components/schemas/BenefitBehaviorRequest"
          },
          "code": {
            "description": "The code staff scan or type to redeem the benefit. Omitted on an update, the current code is kept.",
            "$ref": "#/components/schemas/BenefitCode"
          }
        },
        "additionalProperties": false,
        "description": "Base request model for benefit operations."
      },
      "BenefitStatus": {
        "enum": [
          "Scheduled",
          "Active",
          "Used",
          "Expired",
          "Removed"
        ],
        "type": "string",
        "description": "What a benefit is doing right now, in the terms an operator answers the holder in."
      },
      "BenefitTemplate": {
        "required": [
          "id",
          "type"
        ],
        "type": "object",
        "properties": {
          "id": {
            "minLength": 1,
            "type": "string",
            "description": "The benefit template's key, unique within the tenant and fixed once created."
          },
          "name": {
            "maxLength": 200,
            "type": [
              "null",
              "string"
            ],
            "description": "Name operators know the benefit template by in the admin console and in automations. Never shown\nto the holder, who sees Neo.Web.Api.Benefit.Controllers.BenefitTemplatesController.BenefitTemplate.Content's title instead."
          },
          "enabled": {
            "type": "boolean",
            "description": "Whether the benefit template can be granted. A disabled one is refused by the single-pass grant\n(404) and skipped by automations and campaigns, without error."
          },
          "priority": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Rank of the issued benefit among the others on the same pass. Higher comes first; a benefit\nwith no priority comes after every benefit with one.",
            "format": "int32"
          },
          "activationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When benefits issued from this benefit template become redeemable. Omit for straight away. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "validityMode": {
            "description": "How each issued benefit's end of validity (its `deactivationDate`) is computed. Omit for\nbenefits that never expire.",
            "$ref": "#/components/schemas/BenefitTemplateValidityMode"
          },
          "fixedDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "The instant every issued benefit stops being redeemable. Required when Neo.Web.Api.Benefit.Controllers.BenefitTemplatesController.BenefitTemplate.ValidityMode\nis `FixedDate`, unused otherwise. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "duration": {
            "type": [
              "null",
              "string"
            ],
            "description": "How long each issued benefit stays redeemable, counted from the moment it is issued. Required when\nNeo.Web.Api.Benefit.Controllers.BenefitTemplatesController.BenefitTemplate.ValidityMode is `Duration`, unused otherwise.",
            "format": "date-span"
          },
          "type": {
            "description": "How the issued benefit is consumed: `OneTime` is redeemed once, `MultiUse` counts down\nNeo.Web.Api.Benefit.Controllers.BenefitTemplatesController.BenefitTemplate.InitialValue uses, `Unlimited` is never used up.",
            "$ref": "#/components/schemas/BenefitType"
          },
          "category": {
            "description": "What the benefit gives the holder, used to group and label it on the benefits page and in reports.",
            "$ref": "#/components/schemas/BenefitCategory"
          },
          "tags": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Labels copied onto every issued benefit, for segmenting and reporting. Never shown to the holder."
          },
          "appearance": {
            "description": "Images copied onto every issued benefit. Omit for a benefit with no image.",
            "$ref": "#/components/schemas/BenefitTemplateAppearance"
          },
          "content": {
            "description": "The title and description the holder reads, copied onto every issued benefit.",
            "$ref": "#/components/schemas/BenefitTemplateContent"
          },
          "links": {
            "type": [
              "null",
              "object"
            ],
            "properties": {
              "LegalInformation": {
                "description": "A link shown as a button with the benefit on the benefits page.",
                "$ref": "#/components/schemas/BenefitTemplateLink"
              },
              "CallToAction": {
                "description": "A link shown as a button with the benefit on the benefits page.",
                "$ref": "#/components/schemas/BenefitTemplateLink"
              },
              "TermsAndConditions": {
                "description": "A link shown as a button with the benefit on the benefits page.",
                "$ref": "#/components/schemas/BenefitTemplateLink"
              },
              "PrivacyPolicy": {
                "description": "A link shown as a button with the benefit on the benefits page.",
                "$ref": "#/components/schemas/BenefitTemplateLink"
              },
              "HowToUse": {
                "description": "A link shown as a button with the benefit on the benefits page.",
                "$ref": "#/components/schemas/BenefitTemplateLink"
              },
              "Website": {
                "description": "A link shown as a button with the benefit on the benefits page.",
                "$ref": "#/components/schemas/BenefitTemplateLink"
              },
              "Other": {
                "description": "A link shown as a button with the benefit on the benefits page.",
                "$ref": "#/components/schemas/BenefitTemplateLink"
              }
            },
            "additionalProperties": false,
            "description": "Links shown with the benefit on the benefits page, keyed by purpose."
          },
          "initialValue": {
            "type": [
              "null",
              "number"
            ],
            "description": "The number of uses a `MultiUse` benefit starts with - the \"5\" in \"3 of 5 left\".",
            "format": "double"
          },
          "dataContent": {
            "type": [
              "null",
              "string"
            ],
            "description": "Free text copied into each issued benefit's `data.content`, for a pass template or an integration\nto read. Never shown to the holder as such."
          },
          "passType": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of a standalone wallet pass to create for each issued benefit, alongside the holder's\nown pass. Omit for a benefit that lives only on the holder's pass."
          },
          "code": {
            "description": "How each issued benefit gets the code staff scan or type to redeem it. Omit for a benefit with no\ncode.",
            "$ref": "#/components/schemas/BenefitTemplateCodeSettings"
          },
          "removal": {
            "description": "When a benefit issued from this benefit template leaves the pass. Omit to remove it at end of validity.",
            "$ref": "#/components/schemas/BenefitTemplateRemoval"
          },
          "behavior": {
            "description": "Where a benefit issued from this benefit template is surfaced, and what each surface does with it. Omit for the defaults.",
            "$ref": "#/components/schemas/BenefitTemplateBehavior"
          },
          "creationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit template was created. Set by the server; ignored on write. Null on benefit templates\ncreated before it was recorded. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "lastModificationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit template definition last changed. Set by the server on every write; ignored on write. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          }
        },
        "additionalProperties": false,
        "description": "The reusable definition of a benefit: what a holder is given each time it is granted to a pass, by an\nautomation, a campaign or a single grant."
      },
      "BenefitTemplateAppearance": {
        "type": "object",
        "properties": {
          "images": {
            "type": "array",
            "items": {
              "description": "A single image entry within a benefit template appearance.",
              "$ref": "#/components/schemas/BenefitTemplateImage"
            },
            "description": "The images, at most one per slot; where a slot is named twice the last entry wins."
          }
        },
        "additionalProperties": false,
        "description": "The images a benefit template gives each benefit it issues."
      },
      "BenefitTemplateBehavior": {
        "type": "object",
        "properties": {
          "mode": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Where a benefit is shown and what each surface does with it.",
              "$ref": "#/components/schemas/BenefitBehaviorMode"
            },
            "description": "The behaviours an issued benefit carries, one entry per behaviour."
          }
        },
        "additionalProperties": false,
        "description": "Where a benefit issued from the benefit template is surfaced, and what each surface does with it."
      },
      "BenefitTemplateCodeCharset": {
        "enum": [
          "Alphanumeric",
          "Numeric",
          "Alpha",
          "Hex"
        ],
        "type": "string",
        "description": "The characters the random part of an autogenerated code is drawn from."
      },
      "BenefitTemplateCodePattern": {
        "type": "object",
        "properties": {
          "length": {
            "type": "integer",
            "description": "Number of random characters, prefix and suffix excluded. Between the charset's minimum (Numeric 9,\nAlpha 7, Hex 8, Alphanumeric 6) and 64.",
            "format": "int32"
          },
          "charset": {
            "description": "The characters the random part is drawn from. `ean13` requires `Numeric`.",
            "$ref": "#/components/schemas/BenefitTemplateCodeCharset"
          },
          "prefix": {
            "type": [
              "null",
              "string"
            ],
            "description": "Fixed text placed before the random part, e.g. a campaign marker. Digits only for `ean13`."
          },
          "suffix": {
            "type": [
              "null",
              "string"
            ],
            "description": "Fixed text placed after the random part. Digits only for `ean13`."
          },
          "uppercase": {
            "type": "boolean",
            "description": "Whether letters in the random part are upper-case (default) or lower-case. Prefix and suffix are kept as written."
          }
        },
        "additionalProperties": false,
        "description": "The shape of a randomly drawn code."
      },
      "BenefitTemplateCodeSettings": {
        "type": "object",
        "properties": {
          "format": {
            "description": "How the code is rendered to the holder: a barcode symbology, or `raw` for text only.",
            "$ref": "#/components/schemas/BenefitCodeFormat"
          },
          "valueMode": {
            "description": "Where the code value comes from: `Shared` uses Neo.Web.Api.Benefit.Controllers.BenefitTemplatesController.BenefitTemplateCodeSettings.Value for every holder,\n`Autogenerated` draws a random one per benefit from Neo.Web.Api.Benefit.Controllers.BenefitTemplatesController.BenefitTemplateCodeSettings.Pattern, `Custom` runs\nNeo.Web.Api.Benefit.Controllers.BenefitTemplatesController.BenefitTemplateCodeSettings.Script. Omit for no code.",
            "$ref": "#/components/schemas/BenefitTemplateCodeValueMode"
          },
          "value": {
            "type": [
              "null",
              "string"
            ],
            "description": "The code every holder gets, e.g. a promotion code typed at checkout. Required when\nNeo.Web.Api.Benefit.Controllers.BenefitTemplatesController.BenefitTemplateCodeSettings.ValueMode is `Shared`."
          },
          "pattern": {
            "description": "Shape of the random code drawn for each benefit. Used when Neo.Web.Api.Benefit.Controllers.BenefitTemplatesController.BenefitTemplateCodeSettings.ValueMode is\n`Autogenerated`; omitted, a 10-character upper-case alphanumeric code is drawn.",
            "$ref": "#/components/schemas/BenefitTemplateCodePattern"
          },
          "script": {
            "type": [
              "null",
              "string"
            ],
            "description": "Body of the JavaScript function that returns the code, without its wrapper, e.g.\n`return \"X-\" + Date.now();`. Required when Neo.Web.Api.Benefit.Controllers.BenefitTemplatesController.BenefitTemplateCodeSettings.ValueMode is `Custom`."
          }
        },
        "additionalProperties": false,
        "description": "How each benefit issued from this benefit template gets its code, and how the code is rendered."
      },
      "BenefitTemplateCodeValueMode": {
        "enum": [
          "Shared",
          "Autogenerated",
          "Custom"
        ],
        "type": "string",
        "description": "Where the code of a benefit issued from a benefit template comes from."
      },
      "BenefitTemplateContent": {
        "type": "object",
        "properties": {
          "title": {
            "description": "The benefit's name as the holder sees it, on the benefits page and as a wallet pass field. Required\non create; a benefit without one is shown as \"Untitled benefit\".",
            "$ref": "#/components/schemas/BenefitTemplateLocalizedString"
          },
          "description": {
            "description": "What the benefit gives and how to use it, shown on the benefits page and, when the behaviour asks for\nit, on the back of the wallet pass.",
            "$ref": "#/components/schemas/BenefitTemplateLocalizedString"
          }
        },
        "additionalProperties": false,
        "description": "The holder-facing texts of a benefit template."
      },
      "BenefitTemplateImage": {
        "required": [
          "slot",
          "url"
        ],
        "type": "object",
        "properties": {
          "slot": {
            "description": "Where the image is used: `main` for the headline visual, `thumbnail` for compact lists.",
            "$ref": "#/components/schemas/BenefitImageSlot"
          },
          "url": {
            "description": "The image, per language. Each value is an `http`/`https` address, or the name of a file\nuploaded to this benefit template through `POST {id}/images` (e.g. `hero.png`).",
            "$ref": "#/components/schemas/BenefitTemplateLocalizedString"
          }
        },
        "additionalProperties": false,
        "description": "A single image entry within a benefit template appearance."
      },
      "BenefitTemplateImageInfo": {
        "type": "object",
        "properties": {
          "path": {
            "type": "string",
            "description": "Image path, `public/benefitTemplates/{id}/{name}`: the value to put in the benefit template's\n`appearance.images[].url`. The bare file name is accepted there too."
          },
          "name": {
            "type": "string",
            "description": "The file name as stored, e.g. `hero.png`; uploading the same name again replaces the image."
          }
        },
        "additionalProperties": false,
        "description": "Holds the path and file name of a benefit template image."
      },
      "BenefitTemplateLink": {
        "required": [
          "link"
        ],
        "type": "object",
        "properties": {
          "title": {
            "description": "The button label. At most 100 characters per language.",
            "$ref": "#/components/schemas/BenefitTemplateLocalizedString"
          },
          "link": {
            "type": "string",
            "description": "The address the button opens: an absolute `https` URI.",
            "format": "uri"
          }
        },
        "additionalProperties": false,
        "description": "A link shown as a button with the benefit on the benefits page."
      },
      "BenefitTemplateLocalizedString": {
        "required": [
          "default"
        ],
        "type": "object",
        "properties": {
          "default": {
            "minLength": 1,
            "type": "string",
            "description": "The text shown to a holder whose language has no entry in Neo.Web.Api.Benefit.Controllers.BenefitTemplatesController.BenefitTemplateLocalizedString.Localizations."
          },
          "localizations": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "string"
            },
            "description": "Per-language overrides, keyed by language code (e.g. `fr`, `en-US`)."
          }
        },
        "additionalProperties": false,
        "description": "A string with a mandatory default value and optional per-language overrides."
      },
      "BenefitTemplateRemoval": {
        "type": "object",
        "properties": {
          "mode": {
            "description": "Rule used to compute the benefit's deletion date.",
            "$ref": "#/components/schemas/BenefitTemplateRemovalMode"
          },
          "days": {
            "maximum": 3650,
            "minimum": 1,
            "type": [
              "null",
              "integer"
            ],
            "description": "How many days an expired benefit stays visible on the pass, shown as expired. Required when\nNeo.Web.Api.Benefit.Controllers.BenefitTemplatesController.BenefitTemplateRemoval.Mode is `AfterEndOfValidity`, dropped otherwise.",
            "format": "int32"
          },
          "date": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "The instant every issued benefit leaves the pass. Required when Neo.Web.Api.Benefit.Controllers.BenefitTemplatesController.BenefitTemplateRemoval.Mode is\n`FixedDate`, dropped otherwise. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          }
        },
        "additionalProperties": false,
        "description": "When the benefit issued from this benefit template is removed from the pass."
      },
      "BenefitTemplateRemovalMode": {
        "enum": [
          "Never",
          "EndOfValidity",
          "AfterEndOfValidity",
          "FixedDate"
        ],
        "type": "string",
        "description": "How the deletion date of an issued benefit is derived."
      },
      "BenefitTemplateValidityMode": {
        "enum": [
          "FixedDate",
          "Duration"
        ],
        "type": "string",
        "description": "How the end of validity of a benefit issued from a benefit template is computed."
      },
      "BenefitType": {
        "enum": [
          "OneTime",
          "Unlimited",
          "MultiUse"
        ],
        "type": "string",
        "description": "How a benefit is consumed, which decides what its movements mean and when it is used up."
      },
      "BenefitWithPassRow": {
        "required": [
          "benefitId",
          "passCreationDate",
          "passId",
          "passType",
          "type"
        ],
        "type": "object",
        "properties": {
          "passId": {
            "type": "string",
            "description": "Id of the pass carrying the benefit, for the pass endpoints."
          },
          "passType": {
            "type": "string",
            "description": "Pass template of the pass carrying the benefit (e.g. `loyalty`), not of a linked benefit pass."
          },
          "passCreationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the holder's pass was created. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "passLastUpdateDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the holder's pass last changed, if recorded. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "identifiers": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            },
            "description": "The pass's identifiers in the tenant's other systems, keyed by name (e.g. `y2.customerId`), so a\nrow can be traced back to the customer it belongs to."
          },
          "metadata": {
            "type": "object",
            "additionalProperties": {
              "type": "null"
            },
            "description": "The pass's metadata, as stored on it by the tenant's integrations."
          },
          "benefitId": {
            "type": "string",
            "description": "Id of the benefit, for the benefit endpoints."
          },
          "type": {
            "description": "How the benefit is consumed: `OneTime`, `MultiUse` or `Unlimited`.",
            "$ref": "#/components/schemas/BenefitType"
          },
          "value": {
            "type": "number",
            "description": "The uses left: the sum of every movement. For `Unlimited` it is a tally of what was taken, not a\nstock.",
            "format": "double"
          },
          "target": {
            "type": [
              "null",
              "number"
            ],
            "description": "The number of uses a `MultiUse` benefit started with - the denominator of \"3 of 5 left\". Null when\nthere is no allowance.",
            "format": "double"
          },
          "creationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit was issued. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "lastModificationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit last changed — a patch, or a movement applied. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "activationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit becomes redeemable (null = straight away). Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "deactivationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit stops being redeemable (null = never expires). Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "deletionDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the benefit is removed from the pass (null = never removed). Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "originProcessId": {
            "type": [
              "null",
              "string"
            ],
            "description": "The benefit's `origin.processId`: the id of the benefit template that issued it, or the\nintegration's own process id. Filter on `origin.processId` to list one campaign's benefits."
          },
          "lastMovement": {
            "description": "The latest movement - typically the last redemption - so a row can show it without loading the history.",
            "$ref": "#/components/schemas/BenefitMovementSummary"
          },
          "movementCount": {
            "type": "integer",
            "description": "Number of movements, the opening one included.",
            "format": "int32"
          },
          "tags": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "The benefit's tags, for segmenting and reporting."
          }
        },
        "additionalProperties": false,
        "description": "One benefit and the pass carrying it, flattened into a single row for the benefits search and its Excel\nexport."
      },
      "BloomreachCacheResponse": {
        "type": "object",
        "properties": {
          "customer": {
            "type": [
              "null",
              "string"
            ],
            "description": "How long a customer read from Bloomreach is reused, as `d.hh:mm:ss`. Null, zero or negative: the\ncustomer cache is off.",
            "format": "date-span"
          }
        },
        "additionalProperties": false,
        "description": "How long Bloomreach lookups are reused."
      },
      "BloomreachConfigurationResponse": {
        "required": [
          "apiKeyId",
          "baseUrl",
          "hasApiKeySecret",
          "projectToken"
        ],
        "type": "object",
        "properties": {
          "projectToken": {
            "minLength": 1,
            "type": "string",
            "description": "Token of the Bloomreach project customers are read from and events are tracked into."
          },
          "baseUrl": {
            "type": "string",
            "description": "Root of the Bloomreach API, as stored.",
            "format": "uri"
          },
          "apiKeyId": {
            "minLength": 1,
            "type": "string",
            "description": "Identifier of the Bloomreach API key the integration uses."
          },
          "hasApiKeySecret": {
            "type": "boolean",
            "description": "Whether an API key secret is stored. When true, a PUT may omit `apiKeySecret` to keep it."
          },
          "cache": {
            "description": "How long Bloomreach lookups are reused. Null when no cache is configured: nothing is cached.",
            "$ref": "#/components/schemas/BloomreachCacheResponse"
          }
        },
        "additionalProperties": false,
        "description": "The tenant's Bloomreach connection, without the API key secret."
      },
      "BloomreachScriptsDefinition": {
        "required": [
          "contactFinder",
          "customerMapper",
          "eventInterceptor"
        ],
        "type": "object",
        "properties": {
          "contactFinder": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          },
          "customerMapper": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          },
          "eventInterceptor": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          }
        },
        "additionalProperties": false,
        "description": "The scripts the Bloomreach integration can be customised with."
      },
      "CegidY2BusinessNotificationSettingsRequest": {
        "type": "object",
        "properties": {
          "webServiceCredentials": {
            "description": "Business notification user (BNU) the subscription is managed with. Required when the connection's\n`listenToBusinessNotification` is true; refused with 400 otherwise.",
            "$ref": "#/components/schemas/CegidY2WebServiceCredentialsRequest"
          }
        },
        "additionalProperties": false,
        "description": "Business notification settings of a connection, in the Cegid Y2 PUT request body."
      },
      "CegidY2BusinessNotificationSettingsResponse": {
        "type": "object",
        "properties": {
          "webServiceCredentials": {
            "description": "Business notification user (BNU) the subscription is managed with. Null when none is stored.",
            "$ref": "#/components/schemas/CegidY2WebServiceCredentialsResponse"
          }
        },
        "additionalProperties": false,
        "description": "Business notification settings of a connection, in the Cegid Y2 GET response body."
      },
      "CegidY2CacheSettings": {
        "type": "object",
        "properties": {
          "customer": {
            "type": [
              "null",
              "string"
            ],
            "description": "Reuse of a Y2 customer read by its customer id.",
            "format": "date-span"
          },
          "loyalty": {
            "type": [
              "null",
              "string"
            ],
            "description": "Reuse of the loyalty card reads: a customer's cards, and one card by its id.",
            "format": "date-span"
          },
          "saleDocuments": {
            "type": [
              "null",
              "string"
            ],
            "description": "Reuse of the sale document reads: a customer's sale document list, and one sale document by its key.",
            "format": "date-span"
          },
          "cashOperations": {
            "type": [
              "null",
              "string"
            ],
            "description": "Reuse of the cash operation reads: a customer's vouchers (bons), and the available amount of one voucher.",
            "format": "date-span"
          }
        },
        "additionalProperties": false,
        "description": "How long Y2 answers are reused before Y2 is asked again, shared between the Cegid Y2 request and response\nbodies. Durations are `d.hh:mm:ss` strings, e.g. `00:05:00`; a null or zero duration does not cache\nthat lookup."
      },
      "CegidY2ConfigurationResponse": {
        "required": [
          "connections",
          "rateLimit",
          "updateCustomerOnPassInstallationChange"
        ],
        "type": "object",
        "properties": {
          "connections": {
            "type": "array",
            "items": {
              "description": "One Y2 server connection, in the Cegid Y2 GET response body.",
              "$ref": "#/components/schemas/CegidY2ConnectionResponse"
            },
            "description": "Y2 server connections, in the stored order, without their passwords."
          },
          "updateCustomerOnPassInstallationChange": {
            "type": "boolean",
            "description": "Whether the Y2 customer is updated when the holder installs the pass on a first device or removes it from\nthe last one."
          },
          "cache": {
            "description": "Cache durations of the Y2 lookups. Null when no cache settings are stored, which disables caching.",
            "$ref": "#/components/schemas/CegidY2CacheSettings"
          },
          "rateLimit": {
            "description": "Client-side rate limiting; the defaults when none are stored.",
            "$ref": "#/components/schemas/CegidY2RateLimitSettings"
          }
        },
        "additionalProperties": false,
        "description": "Response body for the Cegid Y2 configuration."
      },
      "CegidY2ConnectionRequest": {
        "required": [
          "databaseId",
          "name",
          "serviceUrl",
          "userName"
        ],
        "type": "object",
        "properties": {
          "name": {
            "minLength": 1,
            "type": "string",
            "description": "Identifies the connection. Unique within the request (compared case-sensitively), refused with 400 when\nrepeated."
          },
          "isDefault": {
            "type": "boolean",
            "description": "Whether this connection serves the calls no store maps to another connection, including every call made\noutside a store context. Exactly one connection is the default, refused with 400 otherwise. Default false.",
            "default": false
          },
          "serviceUrl": {
            "minLength": 1,
            "type": "string",
            "description": "Base URL of the Y2 services. A trailing `/` is added when missing."
          },
          "userName": {
            "minLength": 1,
            "type": "string",
            "description": "Y2 user the integration calls Y2 with."
          },
          "password": {
            "type": [
              "null",
              "string"
            ],
            "description": "Password of Neo.Extensions.Cegid.Controllers.CegidY2ConnectionRequest.UserName. Omitted or blank, the password stored for the connection of the same\n`name` is kept; refused with 400 when none is stored."
          },
          "databaseId": {
            "minLength": 1,
            "type": "string",
            "description": "Y2 database (folder) the calls target."
          },
          "listenToBusinessNotification": {
            "type": "boolean",
            "description": "Whether Y2 pushes its business notifications (customer, receipt and loyalty card changes) to this platform,\nso the holders' passes follow them. Default false.",
            "default": false
          },
          "businessNotificationSettings": {
            "description": "Business notification settings. Required, with `webServiceCredentials`, when\nNeo.Extensions.Cegid.Controllers.CegidY2ConnectionRequest.ListenToBusinessNotification is true; refused with 400 otherwise.",
            "$ref": "#/components/schemas/CegidY2BusinessNotificationSettingsRequest"
          },
          "receiptSettings": {
            "description": "How the receipt PDFs of this connection are rendered. Null leaves receipt PDFs to the stores'\n`y2.receiptTemplateId` property.",
            "$ref": "#/components/schemas/CegidY2ReceiptSettings"
          }
        },
        "additionalProperties": false,
        "description": "One Y2 server connection, in the Cegid Y2 PUT request body."
      },
      "CegidY2ConnectionResponse": {
        "required": [
          "databaseId",
          "hasPassword",
          "isDefault",
          "listenToBusinessNotification",
          "name",
          "serviceUrl",
          "userName"
        ],
        "type": "object",
        "properties": {
          "name": {
            "minLength": 1,
            "type": "string",
            "description": "Identifies the connection: stores select it through their `y2.connectionName` property or by having\na store id equal to it, and it ends the business notification URL."
          },
          "isDefault": {
            "type": "boolean",
            "description": "Whether this connection serves the calls no store maps to another connection, including every call made\noutside a store context."
          },
          "serviceUrl": {
            "minLength": 1,
            "type": "string",
            "description": "Base URL of the Y2 services, always with a trailing `/`."
          },
          "userName": {
            "minLength": 1,
            "type": "string",
            "description": "Y2 user the integration calls Y2 with."
          },
          "hasPassword": {
            "type": "boolean",
            "description": "Whether a non-blank password is stored for Neo.Extensions.Cegid.Controllers.CegidY2ConnectionResponse.UserName. The password itself is never returned;\nomit it on the PUT to keep it."
          },
          "databaseId": {
            "minLength": 1,
            "type": "string",
            "description": "Y2 database (folder) the calls target."
          },
          "listenToBusinessNotification": {
            "type": "boolean",
            "description": "Whether Y2 pushes its business notifications to this platform for this connection, so the holders' passes\nfollow customer, receipt and loyalty card changes."
          },
          "businessNotificationSettings": {
            "description": "Business notification settings. Null when none are stored.",
            "$ref": "#/components/schemas/CegidY2BusinessNotificationSettingsResponse"
          },
          "receiptSettings": {
            "description": "How the receipt PDFs of this connection are rendered. Null when none are stored.",
            "$ref": "#/components/schemas/CegidY2ReceiptSettings"
          }
        },
        "additionalProperties": false,
        "description": "One Y2 server connection, in the Cegid Y2 GET response body."
      },
      "CegidY2RateLimitSettings": {
        "type": "object",
        "properties": {
          "enabled": {
            "type": "boolean",
            "description": "Whether calls are counted and limited. When false, calls go to Y2 unthrottled on this side. Default true.",
            "default": true
          },
          "permitLimit": {
            "maximum": 2147483647,
            "minimum": 1,
            "type": "integer",
            "description": "Maximum number of calls per window, at least 1. Default 4980. Cegid allows 5000 per 5 minutes on the\nAdvance plan, 20000 on the Dedicated plan.",
            "format": "int32",
            "default": 4980
          },
          "windowSeconds": {
            "maximum": 2147483647,
            "minimum": 1,
            "type": "integer",
            "description": "Length of the window Neo.Extensions.Cegid.Controllers.CegidY2RateLimitSettings.PermitLimit applies to, in seconds, at least 1. Default 300, Cegid's\nown window.",
            "format": "int32",
            "default": 300
          },
          "retryAfterSeconds": {
            "maximum": 2147483647,
            "minimum": 0,
            "type": "integer",
            "description": "Delay, in seconds, before a throttled call is tried again, used when Cegid's `Retry-After` header\nsupplies none. At least 0, default 60.",
            "format": "int32",
            "default": 60
          },
          "queueAcquireTimeoutSeconds": {
            "maximum": 2147483647,
            "minimum": 0,
            "type": "integer",
            "description": "Maximum time, in seconds, a call over the limit waits for a slot before failing. Default 0: such a call\nfails at once.",
            "format": "int32",
            "default": 0
          },
          "queueRetryDelaySeconds": {
            "maximum": 2147483647,
            "minimum": 1,
            "type": "integer",
            "description": "Interval, in seconds, at which a waiting call checks for a free slot, at least 1. Default 1. Used only when\nNeo.Extensions.Cegid.Controllers.CegidY2RateLimitSettings.QueueAcquireTimeoutSeconds is above 0.",
            "format": "int32",
            "default": 1
          }
        },
        "additionalProperties": false,
        "description": "Client-side rate limiting of the calls to Y2, shared between the Cegid Y2 request and response bodies. Keeps\nthe calls to Y2 under the quota of the tenant's Cegid plan."
      },
      "CegidY2ReceiptSettings": {
        "type": "object",
        "properties": {
          "templateId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Y2 report template the receipt PDF is rendered with, e.g. `ZDE`."
          },
          "duplicate": {
            "type": "boolean",
            "description": "Whether Y2 renders the receipt PDF as a duplicate rather than as the original. Default false.",
            "default": false
          }
        },
        "additionalProperties": false,
        "description": "Receipt settings of a connection, shared between the Cegid Y2 request and response bodies."
      },
      "CegidY2ScriptsDefinition": {
        "required": [
          "advisorRepository",
          "connectionInterceptor",
          "mapper"
        ],
        "type": "object",
        "properties": {
          "mapper": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          },
          "advisorRepository": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          },
          "connectionInterceptor": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          }
        },
        "additionalProperties": false,
        "description": "The scripts the Cegid Y2 integration can be customised with."
      },
      "CegidY2WebServiceCredentialsRequest": {
        "required": [
          "userName"
        ],
        "type": "object",
        "properties": {
          "userName": {
            "minLength": 1,
            "type": "string",
            "description": "Y2 user the business notification subscription is read, created and updated with."
          },
          "password": {
            "type": [
              "null",
              "string"
            ],
            "description": "Password of the business notification user. Omitted or blank, the password stored for the connection of\nthe same `name` is kept; refused with 400 when none is stored."
          }
        },
        "additionalProperties": false,
        "description": "Business notification user credentials of a connection, in the Cegid Y2 PUT request body."
      },
      "CegidY2WebServiceCredentialsResponse": {
        "required": [
          "hasPassword",
          "userName"
        ],
        "type": "object",
        "properties": {
          "userName": {
            "minLength": 1,
            "type": "string",
            "description": "Y2 user the business notification subscription is read, created and updated with."
          },
          "hasPassword": {
            "type": "boolean",
            "description": "Whether a non-blank password is stored for the business notification user. The password itself is never\nreturned; omit it on the PUT to keep it."
          }
        },
        "additionalProperties": false,
        "description": "Business notification user credentials of a connection, in the Cegid Y2 GET response body."
      },
      "CheckinPolicyDefinition": {
        "required": [
          "mode"
        ],
        "type": "object",
        "properties": {
          "mode": {
            "description": "Policy in force. `full` when none is configured, which is the policy applied in that case.",
            "$ref": "#/components/schemas/CheckinPolicyMode"
          }
        },
        "additionalProperties": false,
        "description": "Check-in policy currently applied by this tenant."
      },
      "CheckinPolicyMode": {
        "enum": [
          "noIdentification",
          "none",
          "partial",
          "full"
        ],
        "type": "string",
        "description": "Identification required from a customer collecting a pass through an enrolment form."
      },
      "ComarchConfigurationResponse": {
        "required": [
          "connection",
          "providers",
          "rateLimit"
        ],
        "type": "object",
        "properties": {
          "connection": {
            "description": "How the tenant reaches the Comarch API.",
            "$ref": "#/components/schemas/ComarchConnectionResponse"
          },
          "providers": {
            "description": "How the built-in customer and coupon providers behave. `coupon` is always present.",
            "$ref": "#/components/schemas/ComarchProvidersConfiguration"
          },
          "kafkaConnection": {
            "description": "The Kafka topic the tenant listens to; null when Kafka is not configured.",
            "$ref": "#/components/schemas/ComarchKafkaConnectionResponse"
          },
          "rateLimit": {
            "description": "Cap on the calls sent to Comarch.",
            "$ref": "#/components/schemas/ComarchRateLimitSettings"
          }
        },
        "additionalProperties": false,
        "description": "The stored Comarch configuration of the tenant, without its secrets."
      },
      "ComarchConnectionRequest": {
        "required": [
          "baseUrl",
          "clientId",
          "partnerCode",
          "programCode"
        ],
        "type": "object",
        "properties": {
          "baseUrl": {
            "type": "string",
            "description": "Root URL of the Comarch CLM B2B Gateway API. A trailing slash is added when missing.",
            "format": "uri"
          },
          "clientId": {
            "minLength": 1,
            "type": "string",
            "description": "OAuth2 client id issued by Comarch for the B2B Gateway API."
          },
          "programCode": {
            "minLength": 1,
            "type": "string",
            "description": "Comarch CLM code of the loyalty programme (Comarch `program_code`)."
          },
          "partnerCode": {
            "minLength": 1,
            "type": "string",
            "description": "Comarch code of the tenant's partner; only this partner's stores are looked up."
          },
          "clientSecret": {
            "type": [
              "null",
              "string"
            ],
            "description": "OAuth2 client secret. Never returned.\nOmitted, null or blank keeps the stored secret; refused with a 400 when none is stored yet."
          }
        },
        "additionalProperties": false,
        "description": "How the tenant reaches the Comarch CLM B2B Gateway API, as sent on a save."
      },
      "ComarchConnectionResponse": {
        "required": [
          "baseUrl",
          "clientId",
          "hasClientSecret",
          "partnerCode",
          "programCode"
        ],
        "type": "object",
        "properties": {
          "baseUrl": {
            "type": "string",
            "description": "Root URL of the Comarch CLM B2B Gateway API, always ending with a slash.",
            "format": "uri"
          },
          "clientId": {
            "minLength": 1,
            "type": "string",
            "description": "OAuth2 client id issued by Comarch for the B2B Gateway API."
          },
          "programCode": {
            "minLength": 1,
            "type": "string",
            "description": "Comarch CLM code of the loyalty programme (Comarch `program_code`)."
          },
          "partnerCode": {
            "minLength": 1,
            "type": "string",
            "description": "Comarch code of the tenant's partner; only this partner's stores are looked up."
          },
          "hasClientSecret": {
            "type": "boolean",
            "description": "Whether a client secret is stored. When true, a save may omit `connection.clientSecret` to keep it."
          }
        },
        "additionalProperties": false,
        "description": "How the tenant reaches the Comarch CLM B2B Gateway API, as stored, without the client secret."
      },
      "ComarchCouponConfiguration": {
        "type": "object",
        "properties": {
          "enabled": {
            "type": "boolean",
            "description": "When true, the Comarch coupons of the pass's customer are reconciled with the pass's benefits on every\npass creation and every pass update that recomputes metadata. Default false.",
            "default": false
          },
          "passType": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of a separate pass issued for each synced coupon. Null or blank issues none."
          },
          "usedRetentionDays": {
            "maximum": 3650,
            "minimum": 0,
            "type": "integer",
            "description": "Days a used coupon stays on the pass after the sync first sees it used, 0 to 3650 (else 400). 0 removes it at once. Default 0.",
            "format": "int32",
            "default": 0
          },
          "expiredRetentionDays": {
            "maximum": 3650,
            "minimum": 0,
            "type": "integer",
            "description": "Days an expired coupon stays on the pass, counted from its expiry date, 0 to 3650 (else 400). Default 30.",
            "format": "int32",
            "default": 30
          }
        },
        "additionalProperties": false,
        "description": "How the holder's Comarch coupons become benefits on their passes."
      },
      "ComarchCustomerConfiguration": {
        "type": "object",
        "properties": {
          "retrieveCustomerTransactionBalance": {
            "type": "boolean",
            "description": "When true, the account also carries `comarch.customer.waitingToBookPoints` (points not yet booked),\nat the cost of one more Comarch call per customer lookup. Default false.",
            "default": false
          },
          "updateOnPassInstallationChange": {
            "type": "boolean",
            "description": "When true, every pass install or removal on a device calls the\n`extensions.comarch.walletInstallationCustomerUpdater` script, and the update it returns is sent to\nthe Comarch customer named by the pass's Comarch customer id. Default false.",
            "default": false
          }
        },
        "additionalProperties": false,
        "description": "How the holder's Comarch customer record is read and updated."
      },
      "ComarchKafkaConnectionRequest": {
        "required": [
          "bootstrapServers",
          "topic",
          "username"
        ],
        "type": "object",
        "properties": {
          "bootstrapServers": {
            "minLength": 1,
            "type": "string",
            "description": "Comma-separated list of Kafka bootstrap servers, as `host:port`."
          },
          "username": {
            "minLength": 1,
            "type": "string",
            "description": "Kafka user; must support SASL SCRAM-SHA-512."
          },
          "topic": {
            "minLength": 1,
            "type": "string",
            "description": "Kafka topic Comarch publishes its events to; read with the consumer group `twc`."
          },
          "password": {
            "type": [
              "null",
              "string"
            ],
            "description": "Kafka password. Never returned.\nOmitted, null or blank keeps the stored password; refused with a 400 when none is stored yet."
          }
        },
        "additionalProperties": false,
        "description": "The Comarch Kafka topic the tenant listens to, as sent on a save. Comarch events read from it (customer,\npoint balance, coupon) refresh the passes of the customers they name."
      },
      "ComarchKafkaConnectionResponse": {
        "required": [
          "bootstrapServers",
          "hasPassword",
          "topic",
          "username"
        ],
        "type": "object",
        "properties": {
          "bootstrapServers": {
            "minLength": 1,
            "type": "string",
            "description": "Comma-separated list of Kafka bootstrap servers, as `host:port`."
          },
          "username": {
            "minLength": 1,
            "type": "string",
            "description": "Kafka user; must support SASL SCRAM-SHA-512."
          },
          "topic": {
            "minLength": 1,
            "type": "string",
            "description": "Kafka topic Comarch publishes its events to; read with the consumer group `twc`."
          },
          "hasPassword": {
            "type": "boolean",
            "description": "Whether a Kafka password is stored. When false, no Comarch event is received."
          }
        },
        "additionalProperties": false,
        "description": "The Comarch Kafka topic the tenant listens to, as stored, without the password."
      },
      "ComarchProvidersConfiguration": {
        "required": [
          "customer"
        ],
        "type": "object",
        "properties": {
          "customer": {
            "description": "How the holder's Comarch customer record is read and updated.",
            "$ref": "#/components/schemas/ComarchCustomerConfiguration"
          },
          "coupon": {
            "description": "Coupon sync settings. Always returned; on a save, omit it to keep the current settings.",
            "$ref": "#/components/schemas/ComarchCouponConfiguration"
          }
        },
        "additionalProperties": false,
        "description": "How the built-in Comarch customer and coupon providers behave."
      },
      "ComarchRateLimitSettings": {
        "type": "object",
        "properties": {
          "throttlingLimit": {
            "maximum": 10000,
            "minimum": 1,
            "type": "integer",
            "description": "Maximum calls per second sent to Comarch, 1 to 10000 (else 400). Default 80.",
            "format": "int32",
            "default": 80
          }
        },
        "additionalProperties": false,
        "description": "Cap on the calls this tenant sends to Comarch."
      },
      "ComarchScriptsDefinition": {
        "required": [
          "couponMapper",
          "customerMapper",
          "locationMapper",
          "walletInstallationCustomerUpdater"
        ],
        "type": "object",
        "properties": {
          "customerMapper": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          },
          "locationMapper": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          },
          "walletInstallationCustomerUpdater": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          },
          "couponMapper": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          }
        },
        "additionalProperties": false,
        "description": "The scripts the Comarch integration can be customised with."
      },
      "ConfigSchemaCatalog": {
        "type": "object",
        "properties": {
          "definitions": {
            "type": "object",
            "additionalProperties": { },
            "description": "Every schema by title. References between them are written `#/definitions/{title}`, so\nthe object is a JSON Schema definitions map and can be used as one without rewriting."
          },
          "associations": {
            "type": "array",
            "items": {
              "description": "The rule binding one schema to the files it validates. The same rules decide which schema a file is\nvalidated against when it is saved.",
              "$ref": "#/components/schemas/SchemaAssociation"
            },
            "description": "Which files each schema validates. A file matched by no association has no schema, e.g. web hooks,\nscripts and unknown files."
          }
        },
        "additionalProperties": false,
        "description": "The tenant configuration schemas, and which file each of them validates."
      },
      "ConnectBenefitTemplate": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Benefit template identifier, as found on the benefits of a scanned pass."
          },
          "title": {
            "description": "Title to show staff. A template with no title falls back to its back-office name, then to its id.",
            "$ref": "#/components/schemas/LocalizedText"
          }
        },
        "additionalProperties": false,
        "description": "A benefit template the device accepts."
      },
      "ConnectProfile": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Profile identifier, sent back when starting a session."
          },
          "name": {
            "type": "string",
            "description": "Name shown to staff."
          },
          "description": {
            "type": [
              "null",
              "string"
            ],
            "description": "Free text; null when none."
          },
          "emoji": {
            "type": [
              "null",
              "string"
            ],
            "description": "Icon shown next to the name; null when none."
          },
          "color": {
            "type": [
              "null",
              "string"
            ],
            "description": "Hex colour, `#rrggbb`; null when none."
          },
          "validFrom": {
            "type": [
              "null",
              "string"
            ],
            "description": "First instant the profile can be used, UTC. Null means no start.",
            "format": "date-time"
          },
          "validUntil": {
            "type": [
              "null",
              "string"
            ],
            "description": "Instant the profile stops being usable, UTC. Null means no end.",
            "format": "date-time"
          },
          "schedule": {
            "type": "array",
            "items": {
              "description": "An opening window of a profile: it opens at every occurrence of Cron and stays open\nfor DurationMinutes.",
              "$ref": "#/components/schemas/DeviceProfileWindow"
            },
            "description": "Opening windows. Empty means open all the time within the validity dates."
          },
          "settings": {
            "oneOf": [
              {
                "description": "What a Crew Check scanner does while it runs the profile.",
                "$ref": "#/components/schemas/CrewCheckConnectProfileSettings"
              }
            ],
            "description": "Type-specific settings."
          }
        },
        "additionalProperties": false,
        "description": "A profile as the device runs it. The schedule is evaluated by the device, in its own timezone."
      },
      "ConnectProfileSettingsBase": {
        "type": "object",
        "description": "Type-specific settings of a profile as the device runs it. The JSON carries a `$type` discriminator\nequal to the device type (`CrewCheck`)."
      },
      "ConnectResponse": {
        "type": "object",
        "properties": {
          "settings": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/CrewCheckSettings"
              }
            ],
            "description": "The device's settings, including the rotating barcode secret when the tenant has one."
          },
          "profiles": {
            "type": "array",
            "items": {
              "description": "A profile as the device runs it. The schedule is evaluated by the device, in its own timezone.",
              "$ref": "#/components/schemas/ConnectProfile"
            },
            "description": "Profiles the device can run, in the order it shows them. Empty means the device accepts every\nbenefit. An assigned profile that no longer exists, or is of another device type, is left out."
          },
          "session": {
            "description": "The session the device is running, or null. What to resume after a restart.",
            "$ref": "#/components/schemas/DeviceSessionState"
          },
          "pubSub": {
            "description": "Where the device listens for pushes: `sessionClosed`, and `settingsChanged`, on which it calls\n`GET settings`. Null when push is unavailable; the device then learns of a closed session from\nthe `TWC-Device-Session` response header, and of changed settings on its next refresh.",
            "$ref": "#/components/schemas/PubSubConnection"
          }
        },
        "additionalProperties": false,
        "description": "Everything a device needs to run, returned on connect and on a settings refresh."
      },
      "ConnectResult": {
        "type": "object",
        "properties": {
          "websocketUri": {
            "type": "string",
            "description": "Websocket URL to read the logs from. Valid for 10 seconds: open the socket right away.",
            "format": "uri"
          },
          "sessionId": {
            "type": "string",
            "description": "Watcher session to send to `ping`. Opaque, 32 hexadecimal characters."
          }
        },
        "additionalProperties": false,
        "description": "Where to open the log websocket, and the watcher session that keeps it fed."
      },
      "ConnectScanFilter": {
        "type": "object",
        "properties": {
          "tags": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Tags of the benefit templates to accept."
          },
          "benefitTemplates": {
            "type": "array",
            "items": {
              "description": "A benefit template the device accepts.",
              "$ref": "#/components/schemas/ConnectBenefitTemplate"
            },
            "description": "Benefit templates to accept, with the title to show staff."
          }
        },
        "additionalProperties": false,
        "description": "A benefit is accepted if it carries one of Tags or comes from one of\nBenefitTemplates. Both empty means every benefit is accepted."
      },
      "ConnectionToken": {
        "type": "object",
        "properties": {
          "deviceId": {
            "type": "string",
            "description": "Device the key is bound to; the device sends it in every device route."
          },
          "tenantId": {
            "type": "string",
            "description": "Tenant the device belongs to, the `{tenantId}` of every route it calls."
          },
          "apiKey": {
            "type": "string",
            "description": "Secret to send in the `X-API-KEY` header. Its permissions are limited to the device endpoints of this device, scanning passes, and reading and updating holders' passes."
          },
          "environment": {
            "type": "string",
            "description": "Base URL of the platform the device must call.",
            "format": "uri"
          }
        },
        "additionalProperties": false,
        "description": "What a device needs to start talking to the platform."
      },
      "CreateApiKeyRequest": {
        "required": [
          "name"
        ],
        "type": "object",
        "properties": {
          "name": {
            "maxLength": 200,
            "minLength": 1,
            "type": "string",
            "description": "Key name, unique within the tenant regardless of case. 1 to 200 ASCII letters, digits, hyphens,\nunderscores or dots; cannot be changed afterwards."
          },
          "enabled": {
            "type": "boolean",
            "description": "Whether the key is accepted as soon as it is created. Defaults to `true`."
          },
          "permissions": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Permissions granted to the key: scopes, area wildcards (`area:*`) or `*` for full access.\nAt least one is required."
          }
        },
        "additionalProperties": false,
        "description": "Request body to create an API key."
      },
      "CreateDevice": {
        "type": "object",
        "properties": {
          "type": {
            "description": "Device type to create.",
            "$ref": "#/components/schemas/DeviceType"
          },
          "name": {
            "type": "string",
            "description": "Name shown in the back office: required, at most 200 characters."
          },
          "description": {
            "type": [
              "null",
              "string"
            ],
            "description": "Free text for operators; no length limit."
          },
          "isEnabled": {
            "type": "boolean",
            "description": "Whether the device may connect once it has a key. Default `true`."
          },
          "telemetry": {
            "description": "Telemetry settings; null applies the defaults.",
            "$ref": "#/components/schemas/UpdateTelemetrySettings"
          },
          "profileIds": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Profiles the device can run, in the order it shows them; null means none. Each must exist, be of the\ndevice's type, and appear once."
          }
        },
        "additionalProperties": false,
        "description": "Payload to create a new device."
      },
      "CreateEmailTemplateRequest": {
        "required": [
          "cultures",
          "id"
        ],
        "type": "object",
        "properties": {
          "id": {
            "minLength": 1,
            "type": "string",
            "description": "Identifier the platform sends the template by. 1 to 50 letters, digits, hyphens, underscores, dots or\nspaces, and not `.` or `..`, else 400; 409 when a template with this id already exists."
          },
          "cultures": {
            "type": "object",
            "additionalProperties": {
              "description": "Design source and compiled content of a single template culture.",
              "$ref": "#/components/schemas/EmailTemplateCultureContent"
            },
            "description": "Content of one or more cultures, keyed by culture code. At least one entry; each code 1 to 10 letters,\ndigits, hyphens or underscores, else 400."
          }
        },
        "additionalProperties": false,
        "description": "Request body to create a new email template."
      },
      "CreateEnrolmentFormRequest": {
        "required": [
          "name"
        ],
        "type": "object",
        "properties": {
          "name": {
            "minLength": 1,
            "type": "string",
            "description": "Name of the form. Must contain only letters, digits, hyphens or underscores, from 1 to 50\ncharacters, because it becomes a public URL segment; `locales` is reserved.\nRefused with 400 otherwise, and with 409 when a layout of the tenant already has this name."
          },
          "flow": {
            "type": [
              "null",
              "string"
            ],
            "description": "Flow executed when a customer registers through this form. Required unless `yaml` is used,\nin which case the flow is read from it. Must name an existing registration flow, else 400."
          },
          "localization": {
            "description": "Localization wiring. Omitted means the form pulls no locale resources.",
            "$ref": "#/components/schemas/EnrolmentFormLocalization"
          },
          "yaml": {
            "type": [
              "null",
              "string"
            ],
            "description": "Complete form as YAML, saved exactly as sent. Mutually exclusive with `flow` and\n`localization`, and must not be blank, else 400. Validated like the typed fields before anything\nis saved."
          }
        },
        "additionalProperties": false,
        "description": "Request body to create an enrolment form."
      },
      "CreateFlowRequest": {
        "required": [
          "name",
          "steps"
        ],
        "type": "object",
        "properties": {
          "name": {
            "minLength": 1,
            "type": "string",
            "description": "Name of the flow, what layouts reference it by. Must start with a lowercase letter and contain only\nletters, digits, hyphens or underscores, from 2 to 50 characters, else 400. Refused with 409 when a\nflow with the same name, ignoring case, already exists."
          },
          "type": {
            "type": [
              "null",
              "string"
            ],
            "description": "Type of the flow. Must be a flow type available to the tenant, else 400. Omitted or blank means\n`userRegistration`."
          },
          "steps": {
            "type": "array",
            "items": {
              "description": "One step of a flow.",
              "$ref": "#/components/schemas/FlowStepDefinition"
            },
            "description": "Steps executed by the flow, in order. May be empty."
          }
        },
        "additionalProperties": false,
        "description": "Request body to create a flow."
      },
      "CreateOrUpdateModel": {
        "required": [
          "layout"
        ],
        "type": "object",
        "properties": {
          "layout": {
            "minLength": 1,
            "type": "string",
            "description": "Page of the tenant's web app the short URL redirects to, as a path below\n`{publicUrl}/{tenantId}/`."
          },
          "parameters": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            },
            "description": "Query string parameters added to the layout URL on every visit. A visitor's own query parameter of\nthe same name replaces the stored one."
          },
          "options": {
            "description": "Label, expiration date and id length. Omitted on an update, the label and expiration date are\ncleared.",
            "$ref": "#/components/schemas/WebRedirectOptions"
          }
        },
        "additionalProperties": false,
        "description": "Short URL to create, or the full replacement of an existing one."
      },
      "CreatePassData": {
        "type": "object",
        "allOf": [
          {
            "description": "Fields a caller can set on a pass, at creation or on update.",
            "$ref": "#/components/schemas/PassData"
          }
        ],
        "properties": {
          "extensions": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "null"
            },
            "description": "Initial state of the pass's extensions, keyed by extension name (for example `apple`,\n`google`), stored with the pass."
          }
        },
        "additionalProperties": false,
        "description": "Content of a new pass."
      },
      "CreateRoleRequest": {
        "required": [
          "name",
          "permissions"
        ],
        "type": "object",
        "properties": {
          "name": {
            "maxLength": 200,
            "minLength": 1,
            "type": "string",
            "description": "Role name, unique within the tenant. 1 to 200 ASCII letters, digits, hyphens, underscores or dots.\nCannot be `administrator`, and cannot be changed afterwards."
          },
          "permissions": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Permissions granted by the role: scopes, area wildcards (`area:*`) or `*` for full access.\nAt least one is required. Wildcards are kept as sent and returned expanded on read."
          }
        },
        "additionalProperties": false,
        "description": "Request body to create a role."
      },
      "CreateStoreRequest": {
        "required": [
          "latitude",
          "longitude",
          "storeId"
        ],
        "type": "object",
        "properties": {
          "storeId": {
            "minLength": 1,
            "type": "string",
            "description": "Identifier of the store, as known to the retail system; unique within the tenant regardless of case.\nOnly ASCII letters, digits, hyphens, underscores and dots; cannot be changed afterwards."
          },
          "displayName": {
            "maxLength": 200,
            "type": [
              "null",
              "string"
            ],
            "description": "Display name of the store, up to 200 characters. Optional."
          },
          "address": {
            "type": [
              "null",
              "string"
            ],
            "description": "Postal address of the store, as free text. Optional."
          },
          "longitude": {
            "maximum": 180,
            "minimum": -180,
            "type": "number",
            "description": "Longitude in decimal degrees, between -180 and 180, else 400.",
            "format": "double"
          },
          "latitude": {
            "maximum": 90,
            "minimum": -90,
            "type": "number",
            "description": "Latitude in decimal degrees, between -90 and 90, else 400.",
            "format": "double"
          },
          "altitude": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Altitude in meters. Optional.",
            "format": "int32"
          },
          "availableLanguages": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "ISO 639 codes of the languages spoken in the store. Omitted means none."
          },
          "advisors": {
            "type": "array",
            "items": {
              "description": "Advisor assigned to a store, as submitted through a store write request.",
              "$ref": "#/components/schemas/StoreAdvisorRequest"
            },
            "description": "Advisors working in this store. Omitted means none."
          },
          "additionalProperties": {
            "type": "object",
            "additionalProperties": { },
            "description": "Free-form values attached to the store, read by integrations, e.g. `y2.connectionName`. Omitted\nmeans none."
          }
        },
        "additionalProperties": false,
        "description": "Request body to create a store."
      },
      "CreateTenantUserRequest": {
        "required": [
          "email",
          "role"
        ],
        "type": "object",
        "properties": {
          "email": {
            "minLength": 1,
            "type": "string",
            "description": "E-mail address of the user. An account with this address is reused when it exists; otherwise one is\ncreated."
          },
          "name": {
            "maxLength": 200,
            "type": [
              "null",
              "string"
            ],
            "description": "Display name, up to 200 characters. Only used when a new account is created; an existing account\nkeeps its name."
          },
          "role": {
            "minLength": 1,
            "type": "string",
            "description": "Name of the role to grant on this tenant: `administrator` or one of the tenant's roles, matched\ncase-insensitively, else 400."
          },
          "language": {
            "type": [
              "null",
              "string"
            ],
            "description": "Language the invitee will be addressed in, one of the back-office languages. Only used when no\naccount exists for the e-mail yet; English when omitted or not a back-office language."
          }
        },
        "additionalProperties": false,
        "description": "Request payload for inviting a user to the tenant."
      },
      "CredentialDefinition": {
        "required": [
          "clientEmail",
          "clientId",
          "hasClientSecret",
          "hasPrivateKey",
          "hasRefreshToken",
          "privateKeyId",
          "projectId",
          "type"
        ],
        "type": "object",
        "properties": {
          "type": {
            "type": "string",
            "description": "`type` of the Google credential JSON file, `service_account` for a service account key."
          },
          "projectId": {
            "type": "string",
            "description": "Google Cloud project the service account belongs to (`project_id` of the key file)."
          },
          "quotaProject": {
            "type": [
              "null",
              "string"
            ],
            "description": "Google Cloud project billed for the API calls, when it differs from `projectId`. Null when not set."
          },
          "clientId": {
            "type": "string",
            "description": "OAuth client ID of the service account (`client_id` of the key file)."
          },
          "clientEmail": {
            "type": "string",
            "description": "E-mail of the service account (`client_email` of the key file)."
          },
          "privateKeyId": {
            "type": "string",
            "description": "ID of the private key (`private_key_id` of the key file), to tell which key is in use."
          },
          "hasPrivateKey": {
            "type": "boolean",
            "description": "Whether the private key is set. Without it, no Google Wallet API call can be made."
          },
          "hasClientSecret": {
            "type": "boolean",
            "description": "Whether a client secret is set. A service account key has none."
          },
          "hasRefreshToken": {
            "type": "boolean",
            "description": "Whether a refresh token is set. A service account key has none."
          },
          "additionalProperties": {
            "type": "object",
            "additionalProperties": { },
            "description": "Every other field of the key file, stored and returned as sent."
          }
        },
        "additionalProperties": false,
        "description": "Google Wallet issuer service account credential, with secret material redacted."
      },
      "CredentialRequest": {
        "required": [
          "clientEmail",
          "clientId",
          "privateKeyId",
          "projectId",
          "type"
        ],
        "type": "object",
        "properties": {
          "type": {
            "minLength": 1,
            "type": "string",
            "description": "`type` of the Google credential JSON file, `service_account` for a service account key."
          },
          "projectId": {
            "minLength": 1,
            "type": "string",
            "description": "Google Cloud project the service account belongs to (`project_id` of the key file)."
          },
          "quotaProject": {
            "type": [
              "null",
              "string"
            ],
            "description": "Google Cloud project billed for the API calls, when it differs from `projectId`. Omitted or null clears it."
          },
          "clientId": {
            "minLength": 1,
            "type": "string",
            "description": "OAuth client ID of the service account (`client_id` of the key file)."
          },
          "clientSecret": {
            "type": [
              "null",
              "string"
            ],
            "description": "OAuth client secret, for a user credential. Omit or leave empty to keep the current one."
          },
          "clientEmail": {
            "minLength": 1,
            "type": "string",
            "description": "E-mail of the service account (`client_email` of the key file)."
          },
          "privateKey": {
            "type": [
              "null",
              "string"
            ],
            "description": "PEM-encoded private key (`private_key` of the key file). Omit or leave empty to keep the current\nkey; required the first time Google Wallet is configured."
          },
          "privateKeyId": {
            "minLength": 1,
            "type": "string",
            "description": "ID of the private key (`private_key_id` of the key file)."
          },
          "refreshToken": {
            "type": [
              "null",
              "string"
            ],
            "description": "OAuth refresh token, for a user credential. Omit or leave empty to keep the current one."
          },
          "additionalProperties": {
            "type": "object",
            "additionalProperties": { },
            "description": "Every other field of the key file, stored as sent. Replaces the stored fields."
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure the Google Wallet issuer service account credential."
      },
      "CrewCheckConnectProfileSettings": {
        "required": [
          "$type"
        ],
        "type": "object",
        "allOf": [
          {
            "description": "Type-specific settings of a profile as the device runs it. The JSON carries a `$type` discriminator\nequal to the device type (`CrewCheck`).",
            "$ref": "#/components/schemas/ConnectProfileSettingsBase"
          }
        ],
        "properties": {
          "scanFilter": {
            "description": "Which benefits the device accepts. Empty means every benefit.",
            "$ref": "#/components/schemas/ConnectScanFilter"
          },
          "allowStamps": {
            "type": "boolean",
            "description": "Whether staff can add stamps to a stamp card. Off, scanning a stamp card only shows it."
          },
          "redeemOnScan": {
            "description": "Redemption behaviour on scan.",
            "$ref": "#/components/schemas/RedeemOnScanSettings"
          },
          "$type": {
            "enum": [
              "CrewCheck"
            ],
            "type": "string",
            "description": "Discriminator. Always `CrewCheck` for this shape."
          }
        },
        "additionalProperties": false,
        "description": "What a Crew Check scanner does while it runs the profile."
      },
      "CrewCheckProfileSettings": {
        "required": [
          "$type"
        ],
        "type": "object",
        "allOf": [
          {
            "description": "Settings that depend on the profile's device type. The JSON carries a `$type` discriminator equal to\nthe device type (`CrewCheck`), which must match the profile's `type`.",
            "$ref": "#/components/schemas/DeviceProfileSettingsBase"
          }
        ],
        "properties": {
          "scanFilter": {
            "description": "Which benefits the device accepts. Null or empty means every benefit.",
            "$ref": "#/components/schemas/ScanFilter"
          },
          "allowStamps": {
            "type": "boolean",
            "description": "Whether staff can add stamps to a stamp card while the profile runs. Off, scanning a stamp card only shows it."
          },
          "redeemOnScan": {
            "description": "Redemption behaviour on scan. Null applies the defaults (a 5-second repeat-scan block).",
            "$ref": "#/components/schemas/RedeemOnScanSettings"
          },
          "$type": {
            "enum": [
              "CrewCheck"
            ],
            "type": "string",
            "description": "Discriminator. Always `CrewCheck` for this shape."
          }
        },
        "additionalProperties": false,
        "description": "What a Crew Check scanner does while it runs the profile."
      },
      "CrewCheckSettings": {
        "required": [
          "$type",
          "logoUrl"
        ],
        "type": "object",
        "allOf": [
          {
            "description": "Settings of a device. The JSON carries a `$type` discriminator equal to the device type\n(`CrewCheck`).",
            "$ref": "#/components/schemas/DeviceSettingsBase"
          }
        ],
        "properties": {
          "logoUrl": {
            "type": "string",
            "description": "Absolute URL of the logo the app shows. Taken from the tenant's large favicon, else its logo, else\nits favicon, when the device is created; later branding changes do not update it."
          },
          "nfc": {
            "description": "Keys to read Apple and Google Wallet passes over NFC. Null when the device has none; they cannot be\nset through this API.",
            "$ref": "#/components/schemas/NfcSettings"
          },
          "rotatingBarcode": {
            "description": "What the device needs to check the rotating barcode of a Google Wallet pass. Returned only by\n`connect` and `settings`, and absent when the tenant has no rotating barcode configured.",
            "$ref": "#/components/schemas/RotatingBarcodeSettings"
          },
          "$type": {
            "enum": [
              "CrewCheck"
            ],
            "type": "string",
            "description": "Discriminator. Always `CrewCheck` for this shape."
          }
        },
        "additionalProperties": false,
        "description": "Settings of a Crew Check device."
      },
      "CurrentTenantUser": {
        "required": [
          "email",
          "permissions",
          "userId"
        ],
        "type": "object",
        "properties": {
          "userId": {
            "minLength": 1,
            "type": "string",
            "description": "User id of the signed-in user."
          },
          "email": {
            "minLength": 1,
            "type": "string",
            "description": "E-mail address the user signs in with."
          },
          "displayName": {
            "type": [
              "null",
              "string"
            ],
            "description": "Display name. Null when none was given."
          },
          "role": {
            "type": [
              "null",
              "string"
            ],
            "description": "Name of the role the user holds on this tenant. Always `globalAdministrator` for a global\nadministrator, whatever their tenant role; `administrator` for a tenant administrator."
          },
          "permissions": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Every scope the user holds on this tenant, sorted, with wildcards expanded: the permissions of their\nrole plus any granted to them individually. Every scope available to the tenant for a global\nadministrator. Drives which screens and actions the back-office shows."
          }
        },
        "additionalProperties": false,
        "description": "The signed-in user, as seen from this tenant."
      },
      "CustomDomainAvailability": {
        "enum": [
          "available",
          "unavailable",
          "claimedByThisTenant",
          "unknown"
        ],
        "type": "string",
        "description": "Whether a hostname can be claimed."
      },
      "CustomDomainCertificate": {
        "type": "object",
        "properties": {
          "status": {
            "type": [
              "null",
              "string"
            ],
            "description": "Raw certificate status (e.g. `active`), for support. Null before one exists."
          },
          "expiresOn": {
            "type": [
              "null",
              "string"
            ],
            "description": "When the current certificate expires; null until one is issued.",
            "format": "date-time"
          },
          "autoRenew": {
            "type": "boolean",
            "description": "Whether the certificate renews automatically. Renewal requires the customer's DNS records to stay in\nplace."
          }
        },
        "additionalProperties": false,
        "description": "TLS certificate issued for the hostname."
      },
      "CustomDomainDefinition": {
        "required": [
          "dnsRecords",
          "domain"
        ],
        "type": "object",
        "properties": {
          "domain": {
            "type": "string",
            "description": "Domain mail is sent from."
          },
          "dnsRecords": {
            "type": "array",
            "items": {
              "description": "A DNS record the customer creates at their own provider.",
              "$ref": "#/components/schemas/EmailDnsRecord"
            },
            "description": "Records the customer must create at their DNS provider."
          }
        },
        "additionalProperties": false,
        "description": "Custom domain mail is sent from, with the DNS records it needs."
      },
      "CustomDomainDiagnostics": {
        "type": "object",
        "properties": {
          "cloudflareId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Provider identifier of the custom hostname."
          },
          "cloudflareStatus": {
            "type": [
              "null",
              "string"
            ],
            "description": "Raw hostname status."
          },
          "cloudflareSslStatus": {
            "type": [
              "null",
              "string"
            ],
            "description": "Raw certificate status."
          },
          "domainControlValidationMethod": {
            "type": [
              "null",
              "string"
            ],
            "description": "Domain control validation method: `http` or `txt`."
          },
          "originSni": {
            "type": [
              "null",
              "string"
            ],
            "description": "Origin SNI hostname, when one is set."
          },
          "validationErrors": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Raw validation messages. Usually present shortly after creation, until the customer has added their\nrecords."
          }
        },
        "additionalProperties": false,
        "description": "Raw provisioning detail, for support. Not customer-facing copy."
      },
      "CustomDomainDnsRecord": {
        "type": "object",
        "properties": {
          "type": {
            "type": "string",
            "description": "Record type: `CNAME` for routing, `TXT` for ownership verification."
          },
          "name": {
            "type": "string",
            "description": "Record name, fully qualified: the hostname itself for the CNAME, `asuid.` followed by the hostname for\nthe TXT."
          },
          "value": {
            "type": "string",
            "description": "Value to set: the platform's routing target for the CNAME, the ownership verification token for the\nTXT."
          },
          "purpose": {
            "description": "What breaks if it is missing.",
            "$ref": "#/components/schemas/CustomDomainDnsRecordPurpose"
          }
        },
        "additionalProperties": false,
        "description": "A DNS record the customer creates at their own provider."
      },
      "CustomDomainDnsRecordPurpose": {
        "enum": [
          "routing",
          "ownershipVerification"
        ],
        "type": "string",
        "description": "What a DNS record the customer must create is for. Each record is checked on its own."
      },
      "CustomDomainPreflight": {
        "type": "object",
        "properties": {
          "hostname": {
            "type": "string",
            "description": "The hostname, lowercased and normalised."
          },
          "isValid": {
            "type": "boolean",
            "description": "False when one of the rules below rejected it."
          },
          "rejections": {
            "type": "array",
            "items": {
              "description": "Why a hostname was rejected.",
              "$ref": "#/components/schemas/HostnameRejection"
            },
            "description": "Which rules rejected it. Empty when it may be used."
          },
          "isApex": {
            "type": "boolean",
            "description": "True when the hostname is the root of its DNS zone. Correct for multi-part suffixes such as\n`brand.co.uk` and for delegated subzones."
          },
          "zoneApex": {
            "type": [
              "null",
              "string"
            ],
            "description": "Root of the zone the hostname belongs to, when DNS answered."
          },
          "dnsProvider": {
            "type": [
              "null",
              "string"
            ],
            "description": "Recognised DNS provider, or null when the nameservers are unfamiliar."
          },
          "supportsApex": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether that provider can point a zone root at a hostname. Null means unknown — show the generic\ncaution, never \"no\"."
          },
          "availability": {
            "description": "Whether the hostname can be claimed.",
            "$ref": "#/components/schemas/CustomDomainAvailability"
          }
        },
        "additionalProperties": false,
        "description": "What a preflight found out about a hostname."
      },
      "CustomDomainProbeFailure": {
        "enum": [
          "unreachable",
          "tlsFailure",
          "differentServer",
          "hostNotRewritten",
          "timeout"
        ],
        "type": "string",
        "description": "Why a configuration check did not pass."
      },
      "CustomDomainProbeResult": {
        "type": "object",
        "properties": {
          "passed": {
            "type": "boolean",
            "description": "True when an HTTPS request to the hostname reached this application and arrived identified as that\nhostname."
          },
          "resolvedHost": {
            "type": [
              "null",
              "string"
            ],
            "description": "The host this application reported seeing, when the answer could be read at all; null for an unreachable\nhost, a TLS failure, a timeout or a non-success response. Differs from the hostname on\n`hostNotRewritten`."
          },
          "failure": {
            "description": "Why it did not pass. Null when it did.",
            "$ref": "#/components/schemas/CustomDomainProbeFailure"
          },
          "checkedAt": {
            "type": "string",
            "description": "When the check ran, in UTC.",
            "format": "date-time"
          }
        },
        "additionalProperties": false,
        "description": "Outcome of one configuration check."
      },
      "CustomDomainRecord": {
        "required": [
          "dnsRecords",
          "hostname",
          "isBoundInAzure",
          "isLive",
          "state"
        ],
        "type": "object",
        "properties": {
          "hostname": {
            "type": "string",
            "description": "The hostname, lowercased."
          },
          "state": {
            "description": "Where provisioning has got to.",
            "$ref": "#/components/schemas/CustomDomainState"
          },
          "dnsRecords": {
            "type": "array",
            "items": {
              "description": "A DNS record the customer creates at their own provider.",
              "$ref": "#/components/schemas/CustomDomainDnsRecord"
            },
            "description": "Records the customer must create at their DNS provider. Always both, even once they are in place."
          },
          "isLive": {
            "type": "boolean",
            "description": "True when the tenant's `publicUri` points at this hostname, so end users are sent here."
          },
          "isBoundInAzure": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether the hostname is bound on the platform. Null when this could not be determined, which does not\nmean the ownership record is missing."
          },
          "certificate": {
            "description": "Certificate detail. Null before a certificate is being issued, and whenever its status could not be read.",
            "$ref": "#/components/schemas/CustomDomainCertificate"
          },
          "claimedAt": {
            "type": [
              "null",
              "string"
            ],
            "description": "When the hostname was claimed. Null when this could not be determined.",
            "format": "date-time"
          },
          "lastCheckedAt": {
            "type": [
              "null",
              "string"
            ],
            "description": "When the provisioning status was read to build this record, i.e. the time of the request. Null means the\nstatus could not be read and Neo.Runtime.Security.CustomDomains.CustomDomainRecord.State reflects the tenant configuration only — do not read\ncertificate health from such a record.",
            "format": "date-time"
          },
          "diagnostics": {
            "description": "Raw provisioning detail. Returned only by the GET, to a global administrator; null on every other call,\nincluding the create and activate responses.",
            "$ref": "#/components/schemas/CustomDomainDiagnostics"
          }
        },
        "additionalProperties": false,
        "description": "One custom domain, as the admin API reports it."
      },
      "CustomDomainState": {
        "enum": [
          "pending_dns",
          "validating",
          "ready",
          "active",
          "failed",
          "deleted"
        ],
        "type": "string",
        "description": "Where a custom domain is in provisioning."
      },
      "CustomerPayload": {
        "required": [
          "callbackUrl"
        ],
        "type": "object",
        "properties": {
          "callbackUrl": {
            "type": "string",
            "description": "Base URL of the LiveStore instance that opened the session. Once the holder's account is saved, the form\nredirects to `{callbackUrl}/customers/{customerId}`."
          },
          "customerId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Identifier of the customer in the retail system LiveStore works with (Y2 or UR, per the tenant's LiveStore\nconfiguration). Set on the account as `id.y2.customerId` or `id.ur.customerId`;\nwhen absent, the account gets no customer identifier from the session."
          },
          "storeId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Store the session is opened in. The `storeId` query parameter, when sent, replaces it."
          }
        },
        "additionalProperties": { },
        "description": "The customer a Cegid LiveStore session is opened for."
      },
      "DataWrapper_JsonElement": {
        "required": [
          "Body",
          "Header"
        ],
        "type": "object",
        "properties": {
          "__id": {
            "type": "string",
            "description": "See . A new GUID when the event is raised."
          },
          "__creationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "See . The current UTC time when the event is raised. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "__eventName": {
            "type": "string"
          },
          "Header": {
            "description": "What happened, where and by whom.",
            "$ref": "#/components/schemas/Header"
          },
          "Body": {
            "description": "Key of the entity the notification is about, under `Key`. Its shape depends on\n`Header.EventSource`."
          }
        },
        "additionalProperties": false,
        "description": "A Y2 business notification: what happened, and the key of the entity it happened to."
      },
      "Device": {
        "type": "object",
        "properties": {
          "deviceId": {
            "type": "string",
            "description": "Identifier generated on create (a GUID)."
          },
          "name": {
            "type": "string",
            "description": "Name shown in the back office."
          },
          "description": {
            "type": [
              "null",
              "string"
            ],
            "description": "Free text for operators; null when none."
          },
          "isEnabled": {
            "type": "boolean",
            "description": "Whether the device may connect, refresh its settings and start sessions. A disabled device gets 403 `Device disabled`."
          },
          "type": {
            "description": "Device type.",
            "$ref": "#/components/schemas/DeviceType"
          },
          "settings": {
            "oneOf": [
              {
                "description": "Settings of a Crew Check device.",
                "$ref": "#/components/schemas/CrewCheckSettings"
              }
            ],
            "description": "Type-specific settings, without the rotating barcode settings."
          },
          "profileIds": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Profiles the device can run, in the order it shows them. Empty means the device accepts every benefit."
          },
          "session": {
            "description": "The session the device is running, or null.",
            "$ref": "#/components/schemas/DeviceSessionState"
          }
        },
        "additionalProperties": false,
        "description": "A registered device as the back office sees it."
      },
      "DeviceEndReason": {
        "enum": [
          "manual",
          "scheduleEnded"
        ],
        "type": "string",
        "description": "Why a device ended its own session."
      },
      "DeviceProfile": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Stable identifier, chosen on create and never changed afterwards."
          },
          "type": {
            "description": "Device type the profile is for. Only a device of that type can run it.",
            "$ref": "#/components/schemas/DeviceType"
          },
          "name": {
            "type": "string",
            "description": "Name shown to staff on the device."
          },
          "description": {
            "type": [
              "null",
              "string"
            ],
            "description": "Free text for operators; null when none."
          },
          "emoji": {
            "type": [
              "null",
              "string"
            ],
            "description": "Icon shown next to the name; null when none."
          },
          "color": {
            "type": [
              "null",
              "string"
            ],
            "description": "Hex colour, `#rrggbb`, shown with the icon; null when none."
          },
          "validFrom": {
            "type": [
              "null",
              "string"
            ],
            "description": "First instant the profile can be used, UTC. Null means no start.",
            "format": "date-time"
          },
          "validUntil": {
            "type": [
              "null",
              "string"
            ],
            "description": "Instant the profile stops being usable, UTC. Null means no end.",
            "format": "date-time"
          },
          "schedule": {
            "type": "array",
            "items": {
              "description": "An opening window of a profile: it opens at every occurrence of Cron and stays open\nfor DurationMinutes.",
              "$ref": "#/components/schemas/DeviceProfileWindow"
            },
            "description": "Opening windows. Empty means open all the time within the validity dates."
          },
          "settings": {
            "oneOf": [
              {
                "description": "What a Crew Check scanner does while it runs the profile.",
                "$ref": "#/components/schemas/CrewCheckProfileSettings"
              }
            ],
            "description": "Type-specific settings."
          },
          "warnings": {
            "type": "array",
            "items": {
              "description": "Something about a profile an operator should know, which does not stop it from being saved.",
              "$ref": "#/components/schemas/DeviceProfileWarning"
            },
            "description": "What an operator should fix. Empty when there is nothing."
          }
        },
        "additionalProperties": false,
        "description": "A reusable scan context a device can run (Breakfast, Gate F, Cloakroom): what it accepts, and when."
      },
      "DeviceProfileSettingsBase": {
        "type": "object",
        "description": "Settings that depend on the profile's device type. The JSON carries a `$type` discriminator equal to\nthe device type (`CrewCheck`), which must match the profile's `type`."
      },
      "DeviceProfileWarning": {
        "type": "object",
        "properties": {
          "code": {
            "type": "string",
            "description": "`benefitTemplateMissing` or `filterAcceptsAll`."
          },
          "message": {
            "type": "string",
            "description": "Human-readable explanation."
          },
          "benefitTemplateId": {
            "type": [
              "null",
              "string"
            ],
            "description": "The benefit template concerned, for `benefitTemplateMissing`."
          }
        },
        "additionalProperties": false,
        "description": "Something about a profile an operator should know, which does not stop it from being saved."
      },
      "DeviceProfileWindow": {
        "type": "object",
        "properties": {
          "cron": {
            "type": "string",
            "description": "Cron expression with seconds and no year, the format automations use (`0 0 7 * * *` is every day at\n07:00). A wall-clock time, applied by the device in its own timezone. Trimmed; an unparsable expression\nreturns 400."
          },
          "durationMinutes": {
            "type": "integer",
            "description": "How long the window stays open, 1 to 1440 minutes; outside that range returns 400.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "An opening window of a profile: it opens at every occurrence of Cron and stays open\nfor DurationMinutes."
      },
      "DeviceSessionState": {
        "type": "object",
        "properties": {
          "sessionId": {
            "type": "string",
            "description": "Session identifier, sent by the device as `session.id` baggage."
          },
          "profileId": {
            "type": "string",
            "description": "Profile the device runs."
          },
          "since": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the session started, UTC. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "lastSeen": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "Last request the device made within the session, UTC. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          }
        },
        "additionalProperties": false,
        "description": "A device running one profile."
      },
      "DeviceSettingsBase": {
        "type": "object",
        "properties": {
          "telemetry": {
            "description": "Telemetry settings the device should apply. Always populated: the device's own settings where it\nhas them, the defaults otherwise (`information`, 60 seconds).",
            "$ref": "#/components/schemas/TelemetrySettings"
          }
        },
        "description": "Settings of a device. The JSON carries a `$type` discriminator equal to the device type\n(`CrewCheck`)."
      },
      "DeviceTelemetryBatch": {
        "required": [
          "batchId",
          "items",
          "sentAt"
        ],
        "type": "object",
        "properties": {
          "batchId": {
            "type": "string",
            "description": "Client-generated batch identifier, used as the idempotency key: re-send a batch with the same id after a\ntimeout, and a batch id recently received from the same device is not recorded again and its items are\nreported as deduplicated. Blank returns 400."
          },
          "sentAt": {
            "type": "string",
            "description": "Device clock reading when the batch was sent. The difference against arrival time is the clock\nskew applied to every item.",
            "format": "date-time"
          },
          "appSessionId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Identifier of the app launch the items came from. Not the profile session: that is\nNeo.Runtime.Devices.Telemetry.DeviceTelemetryItem.SessionId."
          },
          "appVersion": {
            "type": [
              "null",
              "string"
            ],
            "description": "App version string, e.g. `1.0.3+1`."
          },
          "platform": {
            "type": [
              "null",
              "string"
            ],
            "description": "Device platform, `android` or `ios`."
          },
          "osVersion": {
            "type": [
              "null",
              "string"
            ],
            "description": "Operating system version."
          },
          "deviceModel": {
            "type": [
              "null",
              "string"
            ],
            "description": "Manufacturer and model, e.g. `Zebra TC22`."
          },
          "items": {
            "type": "array",
            "items": {
              "description": "One telemetry item as the device recorded it.",
              "$ref": "#/components/schemas/DeviceTelemetryItem"
            },
            "description": "The items carried by this batch, at most the limit in the device's telemetry settings (500 by\ndefault); a larger batch is refused whole with 413. Each item is validated on its own: an invalid one\nis counted as rejected without failing the others."
          }
        },
        "additionalProperties": false,
        "description": "A batch of telemetry uploaded by one device in one request."
      },
      "DeviceTelemetryItem": {
        "required": [
          "timestamp",
          "type"
        ],
        "type": "object",
        "properties": {
          "type": {
            "description": "Telemetry kind, deciding which fields are required. An unrecognised kind is counted as rejected.",
            "$ref": "#/components/schemas/DeviceTelemetryItemType"
          },
          "timestamp": {
            "type": "string",
            "description": "Device clock reading when the item was recorded. Corrected by the batch's clock skew and capped at\nthe time the batch arrived. An item without one is counted as rejected.",
            "format": "date-time"
          },
          "severity": {
            "description": "Severity of the item; `information` when omitted. An exception item is always recorded at\n`error` or above, whatever it says here.",
            "$ref": "#/components/schemas/DeviceTelemetrySeverity"
          },
          "name": {
            "type": [
              "null",
              "string"
            ],
            "description": "Item name. Required (non-blank) for Neo.Runtime.Devices.Telemetry.DeviceTelemetryItemType.Event,\nNeo.Runtime.Devices.Telemetry.DeviceTelemetryItemType.Dependency and Neo.Runtime.Devices.Telemetry.DeviceTelemetryItemType.PageView;\nan item without one is counted as rejected."
          },
          "message": {
            "type": [
              "null",
              "string"
            ],
            "description": "Message body. Required (non-blank) for\nNeo.Runtime.Devices.Telemetry.DeviceTelemetryItemType.Trace and Neo.Runtime.Devices.Telemetry.DeviceTelemetryItemType.Exception; an\nitem without one is counted as rejected."
          },
          "sessionId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Profile session the device ran when it recorded the item, as a GUID; an item without a valid one is\nattributed to no session."
          },
          "traceId": {
            "type": [
              "null",
              "string"
            ],
            "description": "W3C trace id (32 hex characters) the device span belonged to. With a valid Neo.Runtime.Devices.Telemetry.DeviceTelemetryItem.SpanId, the\nitem is correlated with the API requests of that trace."
          },
          "spanId": {
            "type": [
              "null",
              "string"
            ],
            "description": "W3C span id (16 hex characters) of the device span. Only used together with Neo.Runtime.Devices.Telemetry.DeviceTelemetryItem.TraceId."
          },
          "durationMs": {
            "type": [
              "null",
              "number"
            ],
            "description": "Duration of the operation in milliseconds, rounded to the millisecond. Meaningful for\ndependency and page-view items.",
            "format": "double"
          },
          "success": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether a dependency call succeeded."
          },
          "resultCode": {
            "type": [
              "null",
              "string"
            ],
            "description": "Result code of a dependency call, typically an HTTP status."
          },
          "properties": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "string"
            },
            "description": "Custom properties recorded with the item. Keys that match a property the platform sets (compared\ncase-insensitively) are not recorded."
          }
        },
        "additionalProperties": false,
        "description": "One telemetry item as the device recorded it."
      },
      "DeviceTelemetryItemType": {
        "enum": [
          "trace",
          "exception",
          "event",
          "dependency",
          "pageView",
          "unknown"
        ],
        "type": "string",
        "description": "Kind of telemetry an item carries."
      },
      "DeviceTelemetrySeverity": {
        "enum": [
          "verbose",
          "information",
          "warning",
          "error",
          "critical"
        ],
        "type": "string",
        "description": "Severity of a telemetry item, in the vocabulary the client logger uses. Ordered: each value is more\nsevere than the one before, which is what a device's minimum severity setting compares against."
      },
      "DeviceType": {
        "enum": [
          "CrewCheck"
        ],
        "type": "string",
        "description": "Kind of device, which decides its settings, the profiles it can run and the permissions of its API key."
      },
      "DiscoverableProgramRequest": {
        "type": "object",
        "properties": {
          "classId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Full Google class id to create or update. Omitted, the class `{issuerId}.loyalty-{countryCode}-discoveryprogram` is used, with an environment suffix outside production."
          },
          "countryCode": {
            "type": "string",
            "description": "ISO 3166-1 alpha-2 country the program is offered in. Required; an unknown code is refused with 400."
          },
          "programName": {
            "type": [
              "null",
              "string"
            ],
            "description": "Program name, used only when `localizedProgramName` is empty."
          },
          "programLogo": {
            "type": "string",
            "description": "Public URL of the program logo, fetched by Google. Required."
          },
          "issuerName": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            },
            "description": "Issuer name keyed by language code. Required; the first entry becomes the default language."
          },
          "localizedProgramName": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "string"
            },
            "description": "Program name keyed by language code; the first entry becomes the default language and the plain program name."
          },
          "signinUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "Page where an existing member signs in to link their account. Omitted, sign-in is removed from the program."
          },
          "signupUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "Page where a new holder joins the program. Omitted together with `signupSharedDatas`, sign-up is removed from the program."
          },
          "signupSharedDatas": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Holder data Google shares with the sign-up page, as Google shared data types. Any casing is accepted (`firstName`, `first-name` and `FIRST_NAME` are equivalent); blanks, duplicates and `SHARED_DATA_TYPE_UNSPECIFIED` are dropped."
          }
        },
        "additionalProperties": false,
        "description": "The discoverable program to publish on a loyalty class."
      },
      "DiscoverableProgramResponse": {
        "type": "object",
        "properties": {
          "classId": {
            "type": "string",
            "description": "Full Google class id, `{issuerId}.{suffix}`."
          },
          "countryCode": {
            "type": "string",
            "description": "ISO 3166-1 alpha-2 country the program is offered in. Empty when Google has none on the class."
          },
          "programName": {
            "type": "string",
            "description": "Program name in the class's default language; empty when unset."
          },
          "programLogo": {
            "type": [
              "null",
              "string"
            ],
            "description": "Public URL of the program logo; null when the class has none."
          },
          "issuerName": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "string"
            },
            "description": "Issuer name keyed by language code. A class with only a plain, unlocalized name returns it under `en`; null when there is no name at all."
          },
          "localizedProgramName": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "string"
            },
            "description": "Program name keyed by language code, with the same fallback to `en` as `issuerName`."
          },
          "signinUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "Page where an existing member signs in to link their account; null when not set."
          },
          "signupUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "Page where a new holder joins the program; null when not set."
          },
          "signupSharedDatas": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Holder data Google shares with the sign-up page, as upper snake case Google shared data types (for example `FIRST_NAME`, `EMAIL_OR_PHONE`); null when none."
          },
          "state": {
            "type": [
              "null",
              "string"
            ],
            "description": "Publication state of the program (trusted testers only, live, or disabled), set by Google and passed through as Google reports it; null when Google has not set one."
          }
        },
        "additionalProperties": false,
        "description": "A loyalty class and the discoverable program it publishes in the Google Wallet app."
      },
      "DownloadPageDefinition": {
        "required": [
          "localization",
          "name",
          "requireValidRedirectId",
          "type",
          "yaml"
        ],
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "Name of the page."
          },
          "type": {
            "description": "Kind of page. Fixed at creation.",
            "$ref": "#/components/schemas/DownloadPageType"
          },
          "headerImage": {
            "type": [
              "null",
              "string"
            ],
            "description": "Image shown in the header, as a URL. `/public/…` for an image stored in the tenant\nconfiguration. Null when the page shows none."
          },
          "requireValidRedirectId": {
            "type": "boolean",
            "description": "Whether the page refuses traffic that does not come through a valid short link."
          },
          "autoDownloadPass": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether the pass is downloaded without the customer acting. `pass` pages only."
          },
          "passCreation": {
            "description": "Pass creation wiring. Null when the page does not create passes.",
            "$ref": "#/components/schemas/DownloadPagePassCreation"
          },
          "allowDownloadAllPasses": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether a download-everything button is offered. `passList` and `benefitList` pages only."
          },
          "showInactivePasses": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether inactive passes are listed, undownloadable. `passList` pages only."
          },
          "localization": {
            "description": "Localization wiring and translated strings.",
            "$ref": "#/components/schemas/DownloadPageLocalization"
          },
          "yaml": {
            "type": "string",
            "description": "The page as YAML, verbatim."
          }
        },
        "additionalProperties": false,
        "description": "Full definition of a download page, returned by the get/create/save endpoints."
      },
      "DownloadPageListItem": {
        "required": [
          "localeResourceCount",
          "name",
          "type"
        ],
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "Name of the page, unique within the tenant, and the last segment of its public URL."
          },
          "type": {
            "description": "Kind of page.",
            "$ref": "#/components/schemas/DownloadPageType"
          },
          "passCreationFlow": {
            "type": [
              "null",
              "string"
            ],
            "description": "Flow executed when the page has to create the pass it shows. Null when the page does not create\npasses, and always null for a `passList` or `benefitList` page."
          },
          "localeResourceCount": {
            "type": "integer",
            "description": "Number of translation directories the page reads its strings from.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "Download page returned by the list endpoint."
      },
      "DownloadPageLocalization": {
        "type": "object",
        "properties": {
          "resources": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Translation directories, e.g. `/locales/myPage/`. Order matters when the same string is\ndefined in more than one directory. Translations are read from, and written to, the first one."
          },
          "directory": {
            "type": [
              "null",
              "string"
            ],
            "description": "Directory the translations below are read from and written to. Null when the page declares no\ntranslation directory, in which case translations cannot be saved."
          },
          "translations": {
            "type": "object",
            "additionalProperties": {
              "description": "Translated strings of one culture.",
              "$ref": "#/components/schemas/DownloadPageTranslations"
            },
            "description": "Translated strings, keyed by culture. Cultures with no translations are absent."
          }
        },
        "additionalProperties": false,
        "description": "Localization wiring and translated strings of a download page."
      },
      "DownloadPagePassCreation": {
        "required": [
          "flow",
          "flowExists",
          "flowHasPassStep"
        ],
        "type": "object",
        "properties": {
          "flow": {
            "type": "string",
            "description": "Flow executed to create the pass."
          },
          "flowExists": {
            "type": "boolean",
            "description": "Whether the flow still exists as a registration flow. False means the page cannot create a pass\nany more — the flow was renamed or deleted."
          },
          "flowHasPassStep": {
            "type": "boolean",
            "description": "Whether the flow carries a `pass` step. False means the flow runs but creates no pass, so\nthe page will not show one. Advisory: the configuration is valid either way."
          }
        },
        "additionalProperties": false,
        "description": "How a `pass` page creates the pass it shows, when it is missing."
      },
      "DownloadPageTranslations": {
        "type": "object",
        "properties": {
          "mobile": {
            "description": "Phone strings. `pass` pages only.",
            "$ref": "#/components/schemas/PassMobileTranslations"
          },
          "desktop": {
            "description": "Desktop strings. `pass` pages only.",
            "$ref": "#/components/schemas/PassDesktopTranslations"
          },
          "layout": {
            "description": "Headline strings. `passList` pages only.",
            "$ref": "#/components/schemas/PassListLayoutTranslations"
          },
          "qrCode": {
            "description": "QR code strings. `passList` pages only.",
            "$ref": "#/components/schemas/PassListQrCodeTranslations"
          },
          "benefitList": {
            "description": "Benefit list page strings. `benefitList` pages only.",
            "$ref": "#/components/schemas/BenefitListPageTranslations"
          }
        },
        "additionalProperties": false,
        "description": "Translated strings of one culture."
      },
      "DownloadPageType": {
        "enum": [
          "pass",
          "passList",
          "benefitList"
        ],
        "type": "string",
        "description": "Kind of download page."
      },
      "EmailDnsRecord": {
        "required": [
          "name",
          "purpose",
          "type",
          "value"
        ],
        "type": "object",
        "properties": {
          "type": {
            "type": "string",
            "description": "Record type, `CNAME` or `TXT`."
          },
          "name": {
            "type": "string",
            "description": "Record name, fully qualified."
          },
          "value": {
            "type": "string",
            "description": "Value to set."
          },
          "purpose": {
            "description": "What the record is for.",
            "$ref": "#/components/schemas/EmailDnsRecordPurpose"
          }
        },
        "additionalProperties": false,
        "description": "A DNS record the customer creates at their own provider."
      },
      "EmailDnsRecordPurpose": {
        "enum": [
          "sendgridValidation",
          "dkimPrimary",
          "dkimSecondary",
          "dmarc"
        ],
        "type": "string",
        "description": "What a DNS record of the custom sending domain is for."
      },
      "EmailProviderDefinition": {
        "required": [
          "hasApiKey",
          "starterScript"
        ],
        "type": "object",
        "properties": {
          "type": {
            "type": [
              "null",
              "string"
            ],
            "description": "Provider type as configured: `sendgrid`, `mailchimp`, `script`, or another provider\ntype configured outside this API. Null when this tenant has no email provider configured yet."
          },
          "from": {
            "description": "Sender identity. Null for the `script` provider and when nothing is configured.",
            "$ref": "#/components/schemas/FromDefinition"
          },
          "hasApiKey": {
            "type": "boolean",
            "description": "Whether an API key is currently set. Always false for the `script` provider."
          },
          "customDomain": {
            "description": "Custom sending domain. Null unless the provider is `sendgrid` and a custom sending domain is\nconfigured.",
            "$ref": "#/components/schemas/CustomDomainDefinition"
          },
          "script": {
            "type": [
              "null",
              "string"
            ],
            "description": "Content of the provider script. Null when the tenant has no script yet."
          },
          "starterScript": {
            "type": "string",
            "description": "Starter implementation to seed a new script with."
          }
        },
        "additionalProperties": false,
        "description": "Email provider settings. The API key is never returned."
      },
      "EmailProviderType": {
        "enum": [
          "sendgrid",
          "mailchimp",
          "script"
        ],
        "type": "string",
        "description": "Email provider supported by this endpoint."
      },
      "EmailTemplateCultureContent": {
        "required": [
          "css",
          "html"
        ],
        "type": "object",
        "properties": {
          "html": {
            "type": "string",
            "description": "HTML design source, reloaded into the editor; not what is sent. Null is saved as empty."
          },
          "css": {
            "type": "string",
            "description": "CSS design source, reloaded into the editor; not what is sent. Null is saved as empty; empty in a\nresponse when the culture has no CSS."
          },
          "subject": {
            "type": [
              "null",
              "string"
            ],
            "description": "Compiled email subject used to send mail. In a response, null when this culture has no compiled\nsubject and body yet."
          },
          "body": {
            "type": [
              "null",
              "string"
            ],
            "description": "Compiled email body (HTML, with Liquid placeholders) used to send mail. In a response, null when this\nculture has no compiled subject and body yet."
          }
        },
        "additionalProperties": false,
        "description": "Design source and compiled content of a single template culture."
      },
      "EmailTemplateDefinition": {
        "required": [
          "cultures",
          "id"
        ],
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Identifier the platform sends the template by."
          },
          "cultures": {
            "type": "object",
            "additionalProperties": {
              "description": "Design source and compiled content of a single template culture.",
              "$ref": "#/components/schemas/EmailTemplateCultureContent"
            },
            "description": "Content of every culture that has a design source, keyed by culture code."
          }
        },
        "additionalProperties": false,
        "description": "Full definition of an email template, returned by get/create/save endpoints."
      },
      "EmailTemplateListItem": {
        "required": [
          "cultures",
          "id"
        ],
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Identifier the platform sends the template by."
          },
          "cultures": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Culture codes that have a design source, sorted. A culture listed here may still lack a compiled subject and body."
          }
        },
        "additionalProperties": false,
        "description": "Email template returned by the list endpoint."
      },
      "EmailVerificationResult": {
        "type": "object",
        "properties": {
          "isValid": {
            "type": "boolean",
            "description": "`true` when the address is well formed and its domain can receive mail; `false`\n            otherwise."
          }
        },
        "additionalProperties": false,
        "description": "Outcome of an email address check."
      },
      "EnrolmentFormDefinition": {
        "required": [
          "localization",
          "name",
          "yaml"
        ],
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "Name of the form, the last segment of its public URL `/{tenantId}/{name}`."
          },
          "flow": {
            "type": [
              "null",
              "string"
            ],
            "description": "Flow executed when a customer registers through this form. Null when the stored form has none; a\nsave through the typed fields requires one."
          },
          "localization": {
            "description": "Localization wiring of the form.",
            "$ref": "#/components/schemas/EnrolmentFormLocalization"
          },
          "yaml": {
            "type": "string",
            "description": "The form as YAML, exactly as saved."
          }
        },
        "additionalProperties": false,
        "description": "Full definition of an enrolment form, returned by the get/create/save endpoints."
      },
      "EnrolmentFormListItem": {
        "required": [
          "hasForm",
          "localeResourceCount",
          "name"
        ],
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "Name of the form, unique within the tenant, and the last segment of its public URL."
          },
          "flow": {
            "type": [
              "null",
              "string"
            ],
            "description": "Flow executed when a customer registers through this form. Null when the stored form has none."
          },
          "localeResourceCount": {
            "type": "integer",
            "description": "Number of locale resource directories the form pulls its translations from.",
            "format": "int32"
          },
          "hasForm": {
            "type": "boolean",
            "description": "Whether the form declares any fields to fill in."
          }
        },
        "additionalProperties": false,
        "description": "Enrolment form returned by the list endpoint."
      },
      "EnrolmentFormLocalization": {
        "type": "object",
        "properties": {
          "resources": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Locale resource directories, e.g. `/locales/fields/`. Order matters: when the same key is\ndefined in more than one directory, the last one wins. Each directory holds one file per culture,\nmanaged through the enrolment locale endpoints. On a write, a blank entry is refused with 400; a\ndirectory that does not exist yet is accepted."
          }
        },
        "additionalProperties": false,
        "description": "Localization wiring of an enrolment form."
      },
      "EnrolmentLocaleResourceCulture": {
        "required": [
          "culture",
          "formNames",
          "resourceDir",
          "values"
        ],
        "type": "object",
        "properties": {
          "resourceDir": {
            "type": "string",
            "description": "Directory name, as in Neo.Web.Api.Admin.Controllers.Enrolment.EnrolmentLocalesController.EnrolmentLocaleResourceListItem.ResourceDir."
          },
          "culture": {
            "type": "string",
            "description": "Culture of the content, e.g. `en`."
          },
          "formNames": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Enrolment forms whose `internationalization.resources` reference this directory."
          },
          "values": {
            "description": "The saved translations: nested objects whose leaves are strings."
          }
        },
        "additionalProperties": false,
        "description": "One culture's stored content, returned by the get and built by the save endpoint."
      },
      "EnrolmentLocaleResourceListItem": {
        "required": [
          "cultures",
          "formNames",
          "resourceDir"
        ],
        "type": "object",
        "properties": {
          "resourceDir": {
            "type": "string",
            "description": "Directory name under `locales/`, e.g. `fields` for `locales/fields/`."
          },
          "formNames": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Enrolment forms whose `internationalization.resources` reference this directory."
          },
          "cultures": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Cultures that already have translations in the directory."
          }
        },
        "additionalProperties": false,
        "description": "Resource directory returned by the list endpoint."
      },
      "Execution": {
        "required": [
          "duration",
          "id",
          "retryIndex",
          "startDate",
          "success"
        ],
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Id of this delivery: the `executionId` of the execution detail endpoint."
          },
          "startDate": {
            "type": "string",
            "description": "When the delivery started, in UTC.",
            "format": "date-time"
          },
          "retryIndex": {
            "type": "integer",
            "description": "How many times this occurrence was postponed before this delivery; `0` on the first. A\nredelivery after a failure does not increase it.",
            "format": "int32"
          },
          "success": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether the delivery succeeded."
          },
          "duration": {
            "type": [
              "null",
              "string"
            ],
            "description": "How long the delivery ran, serialized as `[d.]hh:mm:ss[.fffffff]`.",
            "format": "date-span"
          }
        },
        "additionalProperties": false,
        "description": "One delivery of an automation run. An occurrence that was postponed appears once per delivery."
      },
      "ExecutionDetail": {
        "required": [
          "logs"
        ],
        "type": "object",
        "allOf": [
          {
            "$ref": "#/components/schemas/Execution"
          }
        ],
        "properties": {
          "logs": {
            "type": "array",
            "items": {
              "description": "One log message or outgoing call recorded for an execution.",
              "$ref": "#/components/schemas/ExecutionLog"
            },
            "description": "Log messages and outgoing calls recorded for the delivery, newest first."
          }
        },
        "additionalProperties": false,
        "description": "An Neo.Web.Api.Scheduler.Controllers.AutomationsController.Execution with the log messages and outgoing calls recorded for it."
      },
      "ExecutionLog": {
        "required": [
          "data",
          "entryType",
          "eventDate",
          "id"
        ],
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Id of the entry."
          },
          "eventDate": {
            "type": "string",
            "description": "When the entry was logged, in UTC.",
            "format": "date-time"
          },
          "entryType": {
            "type": "string",
            "description": "`Trace` for a log message, `Dependencies` for an outgoing call."
          },
          "data": {
            "type": [
              "null",
              "string"
            ],
            "description": "A log message, or for an outgoing call `Data=… ResultCode=… DurationMs=…` (the call's target,\nits result code and its duration in milliseconds)."
          }
        },
        "additionalProperties": false,
        "description": "One log message or outgoing call recorded for an execution."
      },
      "ExecutionSummary": {
        "required": [
          "taskId",
          "taskType"
        ],
        "type": "object",
        "allOf": [
          {
            "$ref": "#/components/schemas/Execution"
          }
        ],
        "properties": {
          "taskId": {
            "type": "string",
            "description": "Id of the automation the run belongs to. It can name an automation deleted since."
          },
          "taskType": {
            "type": [
              "null",
              "string"
            ],
            "description": "The task type that ran: the automation's type (`wallet.pushUpdates`) or a task started on its\nbehalf, such as `dateRelative.backfill`."
          }
        },
        "additionalProperties": false,
        "description": "An Neo.Web.Api.Scheduler.Controllers.AutomationsController.Execution listed across every automation, with the automation it belongs to."
      },
      "ExportTokenRequest": {
        "type": "object",
        "properties": {
          "filters": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "One condition on passes. Several conditions must all hold.",
              "$ref": "#/components/schemas/FilterModel"
            },
            "description": "The filters of `GET benefits`, with the same fields and operators. Omit to export every benefit."
          },
          "sortBys": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "One sort key for pass queries. Several keys apply in order, the first one being the primary sort.",
              "$ref": "#/components/schemas/SortModel"
            },
            "description": "The sort descriptors of `GET benefits`. Omit for an unordered export."
          }
        },
        "additionalProperties": false,
        "description": "Export token request body."
      },
      "ExportTokenResponse": {
        "type": "object",
        "properties": {
          "downloadUrl": {
            "type": "string",
            "description": "Absolute URL of `GET export/download` on the public site, carrying its access token. Valid for 30 minutes; anyone holding it can download the export, so treat it as confidential."
          }
        },
        "additionalProperties": false,
        "description": "A link that downloads the export without any other credential."
      },
      "ExtensionScriptSlot": {
        "required": [
          "conflictingFileNames",
          "endpointName",
          "fileName"
        ],
        "type": "object",
        "properties": {
          "endpointName": {
            "type": "string",
            "description": "The extensibility endpoint the script implements, as passed to `register(...)`, e.g.\n`extensions.comarch.couponMapper`. Fixed per slot."
          },
          "fileName": {
            "type": "string",
            "description": "Name of the script file backing the slot. Returned even when the file does not exist yet."
          },
          "content": {
            "type": [
              "null",
              "string"
            ],
            "description": "The script's content. Null when the tenant has no such file."
          },
          "conflictingFileNames": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Other scripts that register the same endpoint; resolve any entry here so the endpoint has a single\nscript. Empty when there is none."
          }
        },
        "additionalProperties": false,
        "description": "The state of one script slot, as every extension's scripts endpoint returns it."
      },
      "FacebookSignInDefinition": {
        "required": [
          "appId",
          "hasAppSecret"
        ],
        "type": "object",
        "properties": {
          "appId": {
            "type": "string",
            "description": "App ID of the Facebook app customers sign in through. The customer web app starts Facebook login with\nit."
          },
          "hasAppSecret": {
            "type": "boolean",
            "description": "Whether an app secret is configured. The secret itself is never returned; when true, a PUT may omit\n`appSecret` to keep it."
          }
        },
        "additionalProperties": false,
        "description": "Sign in with Facebook settings, without the app secret."
      },
      "FilterAction": {
        "enum": [
          0,
          1
        ],
        "type": "integer",
        "description": "What Y2 does with a notification the filter matches.",
        "format": "int32"
      },
      "FilterInformation": {
        "type": "object",
        "properties": {
          "eventSources": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Y2 service operations the filter matches, in the form of `Header.EventSource`, e.g.\n`Cegid.Retail.Services.ThirdParties.Customers.ICustomerService.Update`."
          },
          "userIds": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Y2 users the filter matches, in the form of `Header.UserId`: the user whose action raised the\nnotification."
          },
          "action": {
            "description": "Whether a matching notification is delivered or dropped.",
            "$ref": "#/components/schemas/FilterAction"
          }
        },
        "additionalProperties": false,
        "description": "A Y2 rule selecting the notifications the subscription delivers or drops."
      },
      "FilterModel": {
        "type": "object",
        "properties": {
          "field": {
            "type": "string",
            "description": "Field to filter by:\n            <list type=\"bullet\"><item>`id`, `passType`, `themeId` — strings.</item><item>`creationDate`, `lastUpdateDate` — UTC dates.</item><item>`installationStatus` — the installed wallets concatenated: `\"\"`, `\"apple\"`, `\"google\"` or `\"applegoogle\"`. Use `contains` to test for one wallet.</item><item>`identifiers.{key}` — an external identifier (string).</item><item>`metadata.{key}` — a metadata field, compared as the type (string, number, boolean, datetime) the tenant's metadata configuration gives it.</item></list>"
          },
          "operator": {
            "description": "Comparison operator to apply. Required; a condition without one is refused with a 400.",
            "$ref": "#/components/schemas/FilterModelOperator"
          },
          "value": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Filter value(s). A value containing `{{`, `{%` or `{#` is first rendered as a Liquid template,\nso relative dates such as `{{ 'now' | date: '%Y-%m-%d' }}` work. Interpretation then depends on\n`Operator` and the metadata field's configured type:\n<list type=\"bullet\"><item><b>String fields</b> (`identifiers.*`, `passType`, `installationStatus`, or `metadata.*` configured as string)\n    — plain string value for most operators; an array of strings for `in` / `notIn`.</item><item><b>Numeric fields</b> (metadata configured as number) — decimal number as a string, e.g. `\"42\"` or `\"3.14\"`.\n    Parsed using invariant culture (`.` as decimal separator).</item><item><b>Boolean fields</b> (metadata configured as boolean) — `\"true\"` or `\"false\"` (case-insensitive).</item><item><b>Date fields</b> (metadata configured as datetime) — ISO 8601 date-time string with timezone, e.g. `\"2024-06-01T00:00:00+00:00\"` or `\"2024-06-01T00:00:00Z\"`.\n    Compared to the second.</item></list>\nThe query parameter name is `value` (repeated for multiple values).\n<example>\nSingle value (equals, contains, startsWith, …):\n```\nGET /passes?filter[0].field=passType&filter[0].operator=equals&filter[0].value=boarding\n```\nMultiple values (in / notIn):\n```\nGET /passes?filter[0].field=passType&filter[0].operator=in&filter[0].value=boarding&filter[0].value=loyalty\n```\nDate comparison (metadata field configured as datetime):\n```\nGET /passes?filter[0].field=metadata.eventDate&filter[0].operator=greaterThan&filter[0].value=2024-01-01T00:00:00Z\n```\nBoolean comparison (metadata field configured as boolean):\n```\nGET /passes?filter[0].field=metadata.isVip&filter[0].operator=equals&filter[0].value=true\n```</example>"
          }
        },
        "additionalProperties": false,
        "description": "One condition on passes. Several conditions must all hold."
      },
      "FilterModelOperator": {
        "enum": [
          "Contains",
          "StartsWith",
          "EndsWith",
          "Equals",
          "IsEmpty",
          "IsNotEmpty",
          "NotEquals",
          "In",
          "NotIn",
          "GreaterThan",
          "LessThan",
          "GreaterThanOrEqual",
          "LessThanOrEqual"
        ],
        "type": "string",
        "description": "How a pass filter compares the field with its value."
      },
      "FlowDefinition": {
        "required": [
          "name",
          "steps",
          "type"
        ],
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "Name of the flow; what layouts reference it by."
          },
          "type": {
            "type": "string",
            "description": "Type of the flow, e.g. `userRegistration`; `userRegistration` when the stored flow has none."
          },
          "steps": {
            "type": "array",
            "items": {
              "description": "One step of a flow.",
              "$ref": "#/components/schemas/FlowStepDefinition"
            },
            "description": "Steps executed by the flow, in order. After a create or save, the steps as sent."
          }
        },
        "additionalProperties": false,
        "description": "Full definition of a flow, returned by the get/create/save endpoints."
      },
      "FlowListItem": {
        "required": [
          "name",
          "stepCount",
          "type"
        ],
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "Name of the flow, unique within the tenant; what layouts reference it by."
          },
          "type": {
            "type": "string",
            "description": "Type of the flow, e.g. `userRegistration`; `userRegistration` when the stored flow has none."
          },
          "stepCount": {
            "type": "integer",
            "description": "Number of steps the flow executes.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "Flow returned by the list endpoint."
      },
      "FlowStepDefinition": {
        "required": [
          "type"
        ],
        "type": "object",
        "properties": {
          "type": {
            "minLength": 1,
            "type": "string",
            "description": "Type of the step, e.g. `mail`, `sms`, `pass` or `script`. On a write, must be a step\ntype available to the tenant, else 400. In a response, empty when the step has none."
          }
        },
        "additionalProperties": { },
        "description": "One step of a flow."
      },
      "FromDefinition": {
        "required": [
          "email"
        ],
        "type": "object",
        "properties": {
          "email": {
            "type": "string",
            "description": "Email address mail is sent from."
          },
          "name": {
            "type": [
              "null",
              "string"
            ],
            "description": "Display name mail is sent from."
          }
        },
        "additionalProperties": false,
        "description": "Sender identity used by the SendGrid and Mailchimp providers."
      },
      "FromRequest": {
        "required": [
          "email"
        ],
        "type": "object",
        "properties": {
          "email": {
            "minLength": 1,
            "type": "string",
            "description": "Email address mail is sent from. Must be a syntactically valid address, else 400.",
            "format": "email"
          },
          "name": {
            "maxLength": 200,
            "type": [
              "null",
              "string"
            ],
            "description": "Display name mail is sent from. Up to 200 characters, else 400.\nOmitted, empty or whitespace stores no name, so the provider shows the address alone."
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure the sender identity."
      },
      "GeneralSecretsDefinition": {
        "type": "object",
        "properties": {
          "secret1": {
            "type": [
              "null",
              "string"
            ],
            "description": "Primary secret: signs the links issued for the tenant, and integrators sign the values they send\nwith it. Null when empty."
          },
          "secret2": {
            "type": [
              "null",
              "string"
            ],
            "description": "Fallback secret: a value signed with it is accepted as well as one signed with `secret1`, so\nintegrators can move from one secret to the next without a cut-over. Not used to sign links. Null\nwhen empty."
          }
        },
        "additionalProperties": false,
        "description": "General secrets of the tenant."
      },
      "GenericEventData": {
        "type": "object",
        "allOf": [
          {
            "description": "A Y2 business notification: what happened, and the key of the entity it happened to.",
            "$ref": "#/components/schemas/DataWrapper_JsonElement"
          }
        ],
        "additionalProperties": false,
        "description": "A Y2 business notification as Y2 posts it, with its body left as raw JSON. Also the payload of the\n`Y2:BusinessNotification:Generic` event, emitted for an event source with no dedicated handling."
      },
      "GoogleClassResponse": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Full Google class id, `{issuerId}.{suffix}`."
          },
          "reviewStatus": {
            "type": [
              "null",
              "string"
            ],
            "description": "Google's review status of the class, passed through as Google reports it (for example `UNDER_REVIEW`, `APPROVED`, `REJECTED`, `DRAFT`); null when Google sends none."
          }
        },
        "additionalProperties": false,
        "description": "A Google Wallet class registered under the tenant's issuer."
      },
      "GoogleClassType": {
        "enum": [
          0,
          1,
          2,
          3,
          4
        ],
        "type": "integer",
        "description": "The Google Wallet class family to read; each family is a separate collection at Google:\n`Loyalty` (loyalty cards), `GiftCard`, `Offer` (coupons), `EventTicket`, `Generic`.",
        "format": "int32"
      },
      "GoogleNfcSettings": {
        "type": "object",
        "properties": {
          "collectorId": {
            "type": "string",
            "description": "Google collector identifier used for NFC tap authentication."
          }
        },
        "additionalProperties": false
      },
      "GoogleSignInDefinition": {
        "required": [
          "clientId"
        ],
        "type": "object",
        "properties": {
          "clientId": {
            "type": "string",
            "description": "OAuth client ID of the Google app customers sign in with. The customer web app starts Google sign-in\nwith it."
          },
          "gtmId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Google Tag Manager container the customer web app loads, e.g. `GTM-XXXX`. Null when none is\nloaded."
          }
        },
        "additionalProperties": false,
        "description": "Sign in with Google settings."
      },
      "GoogleWalletProviderDefinition": {
        "required": [
          "credential",
          "issuerId"
        ],
        "type": "object",
        "properties": {
          "issuerId": {
            "type": "string",
            "description": "Issuer ID from the Google Pay & Wallet Console; prefixes the ID of every Google pass class and object (`{issuerId}.{passId}` by default)."
          },
          "credential": {
            "description": "Service account credential used to call the Google Wallet API.",
            "$ref": "#/components/schemas/CredentialDefinition"
          },
          "webServiceUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "Callback URL Google Wallet notifies when a holder saves or removes a pass. Null means the platform's\nown endpoint, `/api/{tenantId}/passes/google`.",
            "format": "uri"
          }
        },
        "additionalProperties": false,
        "description": "Google Wallet provider settings."
      },
      "Header": {
        "required": [
          "ContentType",
          "EventId",
          "EventSource",
          "SourceId",
          "UserId"
        ],
        "type": "object",
        "properties": {
          "EventId": {
            "type": "string",
            "description": "Y2 identifier of the notification. Carried into the emitted event."
          },
          "EventSource": {
            "type": "string",
            "description": "Y2 service operation that raised the notification, e.g.\n`Cegid.Retail.Services.ThirdParties.Customers.ICustomerService.Update`. Decides how the\nnotification is handled and which shape `Body` must have."
          },
          "ContentType": {
            "type": "string",
            "description": "Y2 service operation that reads the entity designated by `Body`, e.g.\n`…ICustomerService.GetCustomerDetail`. Carried into the emitted event."
          },
          "SourceId": {
            "type": "string",
            "description": "System that raised the notification, `Y2`. Carried into the emitted event."
          },
          "UserId": {
            "type": "string",
            "description": "Y2 user whose action raised the notification. Carried into the emitted event."
          },
          "Date": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When Y2 raised the notification, in UTC. Carried into the emitted event. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          }
        },
        "additionalProperties": false,
        "description": "Header of a Y2 business notification."
      },
      "HostnameRejection": {
        "enum": [
          "malformed",
          "tooLong",
          "wildcard",
          "ownDomain"
        ],
        "type": "string",
        "description": "Why a hostname was rejected."
      },
      "HttpValidationProblemDetails": {
        "type": "object",
        "allOf": [
          {
            "$ref": "#/components/schemas/ProblemDetails"
          }
        ],
        "properties": {
          "errors": {
            "type": "object",
            "additionalProperties": {
              "type": "array",
              "items": {
                "type": "string"
              }
            }
          }
        },
        "additionalProperties": { }
      },
      "InsertBenefitRequest": {
        "required": [
          "type"
        ],
        "type": "object",
        "allOf": [
          {
            "description": "Base request model for benefit operations.",
            "$ref": "#/components/schemas/BenefitRequestBase"
          }
        ],
        "properties": {
          "type": {
            "description": "How the benefit is consumed: `OneTime` is redeemed once, `MultiUse` counts down a number\nof uses, `Unlimited` is never used up.",
            "$ref": "#/components/schemas/BenefitType"
          },
          "category": {
            "description": "What the benefit gives the holder, used to group and label it. `GiftCard` is accepted for\n`MultiUse` only; a refused combination is a 400.",
            "$ref": "#/components/schemas/BenefitCategory"
          },
          "passType": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of a standalone wallet pass to create for this benefit, alongside the holder's own\npass - for a benefit that must be its own card in the wallet, such as a gift card. Null means no\nlinked pass."
          },
          "options": {
            "description": "Additional processing options for benefit creation.",
            "$ref": "#/components/schemas/InsertOptions"
          }
        },
        "additionalProperties": false,
        "description": "Request model to create a new benefit."
      },
      "InsertOptions": {
        "type": "object",
        "properties": {
          "correlationId": {
            "maxLength": 100,
            "minLength": 10,
            "type": [
              "null",
              "string"
            ],
            "description": "The caller's own identifier for this call, e.g. a campaign run id, so support can find every call\nof one batch."
          },
          "notification": {
            "description": "The message to show the holder, in one or several languages.",
            "$ref": "#/components/schemas/NotifyRequest"
          }
        },
        "additionalProperties": false,
        "description": "Configuration options for benefit creation, including correlation tracking and notifications."
      },
      "InvitationStatusResponse": {
        "required": [
          "state"
        ],
        "type": "object",
        "properties": {
          "state": {
            "minLength": 1,
            "type": "string",
            "description": "`valid`: the latest link, not expired, ready to activate. `expired`: the latest link has\n            timed out and the user has never set a password; a new link can be sent. `used`: the access is\n            already activated (the link was spent, or the user already has a password), so the page should offer\n            to sign in. `invalid`: the link cannot be used, for example because the access was removed or a\n            newer link has been sent."
          },
          "tenantName": {
            "type": [
              "null",
              "string"
            ],
            "description": "Display name of the tenant the invitation grants access to. Null when `state` is `invalid`."
          },
          "role": {
            "type": [
              "null",
              "string"
            ],
            "description": "Name of the role the invitation grants on that tenant. Null when `state` is `invalid`."
          },
          "maskedEmail": {
            "type": [
              "null",
              "string"
            ],
            "description": "The invitee's e-mail with the local part hidden, e.g. `j***@brand.com`, so the page can say who\nthe link is for without disclosing the address. Null when `state` is `invalid`."
          },
          "language": {
            "type": [
              "null",
              "string"
            ],
            "description": "The invitee's stored back-office language, for the page to display in. Null when none is stored or\n`state` is `invalid`."
          }
        },
        "additionalProperties": false,
        "description": "What an invitation link currently means."
      },
      "InvitationTokenRequest": {
        "required": [
          "token"
        ],
        "type": "object",
        "properties": {
          "token": {
            "minLength": 1,
            "type": "string",
            "description": "Token from the invitation e-mail's link. A token that cannot be used is not an error, it resolves to\n`invalid`."
          }
        },
        "additionalProperties": false,
        "description": "Request body carrying an invitation link's token."
      },
      "KlaviyoConfigurationResponse": {
        "required": [
          "enableSmsSupport",
          "hasPrivateApiKey",
          "siteId"
        ],
        "type": "object",
        "properties": {
          "siteId": {
            "minLength": 1,
            "type": "string",
            "description": "Klaviyo public API key, also called site ID, as last saved."
          },
          "listId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Klaviyo list the account's consents are synchronised to; `builtin` for Klaviyo's built-in consents\nwithout a list; null when the account's consents are not synchronised. See Neo.Extensions.Klaviyo.Controllers.SetKlaviyoRequest.ListId."
          },
          "enableSmsSupport": {
            "type": "boolean",
            "description": "Whether the account's `consents_sms` consent is synchronised to Klaviyo, in addition to the email consent."
          },
          "hasPrivateApiKey": {
            "type": "boolean",
            "description": "Whether a private API key is stored. When true, a save may omit `privateApiKey` to keep it."
          }
        },
        "additionalProperties": false,
        "description": "The stored Klaviyo connection of the tenant, without its private API key."
      },
      "KlaviyoScriptsDefinition": {
        "required": [
          "mapper",
          "subscriptionsProvider"
        ],
        "type": "object",
        "properties": {
          "mapper": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          },
          "subscriptionsProvider": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          }
        },
        "additionalProperties": false,
        "description": "The scripts the Klaviyo integration can be customised with."
      },
      "LineSignInDefinition": {
        "required": [
          "clientId"
        ],
        "type": "object",
        "properties": {
          "clientId": {
            "type": "string",
            "description": "Channel ID of the LINE Login channel customers sign in through (LINE Developers Console). The customer\nweb app starts LINE Login with it."
          }
        },
        "additionalProperties": false,
        "description": "Sign in with LINE settings."
      },
      "LocalizedString": {
        "type": "object",
        "properties": {
          "value": {
            "type": [
              "null",
              "string"
            ],
            "description": "The default text in the primary language."
          },
          "values": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "string"
            },
            "description": "Localized translations by language code.\nKey: ISO 639-1 code or \"iso2-region\" (e.g., \"en\", \"en-US\").\nValue: The translated string for that language.",
            "propertyNames": {
              "pattern": "^[a-z]{2}(-[A-Z]{2})?$"
            }
          }
        },
        "additionalProperties": false,
        "description": "Represents a localized string with a default value and optional per-language translations."
      },
      "LocalizedText": {
        "type": "object",
        "properties": {
          "default": {
            "type": "string",
            "description": "Text used when no localization matches."
          },
          "localizations": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "string"
            },
            "description": "Translations keyed by language code; null when there are none."
          }
        },
        "additionalProperties": false,
        "description": "A text with its translations."
      },
      "MarketingCloudConfigurationResponse": {
        "required": [
          "hasSigninKey"
        ],
        "type": "object",
        "properties": {
          "hasSigninKey": {
            "type": "boolean",
            "description": "Whether a JWT signing key is stored. When true, a PUT may omit `signinKey` to keep it."
          }
        },
        "additionalProperties": false,
        "description": "The tenant's Salesforce Marketing Cloud settings, without the signing key."
      },
      "MeResponse": {
        "type": "object",
        "properties": {
          "hasTenants": {
            "type": "boolean",
            "description": "Whether the user holds a role on at least one tenant. False for a self-registered user nobody has\ninvited yet, and for a global administrator with no tenant role of their own."
          },
          "emailVerified": {
            "type": "boolean",
            "description": "Whether the user's e-mail address is verified, including a verification done since sign-in."
          },
          "language": {
            "type": [
              "null",
              "string"
            ],
            "description": "The user's back-office language code, e.g. `fr`, or `null` when none is stored."
          }
        },
        "additionalProperties": false,
        "description": "Access state of the signed-in back-office user."
      },
      "MediaImageDefinition": {
        "required": [
          "fileName",
          "size",
          "url"
        ],
        "type": "object",
        "properties": {
          "fileName": {
            "type": "string",
            "description": "File name, extension included. Identifies the image on delete."
          },
          "url": {
            "type": "string",
            "description": "Absolute public URL of the image. A replaced image gets a new URL; earlier URLs serve the current\nimage."
          },
          "lastModified": {
            "type": [
              "null",
              "string"
            ],
            "description": "When the image was last written. Null when unknown, and always null in the upload response.",
            "format": "date-time"
          },
          "size": {
            "type": "integer",
            "description": "Size of the image, in bytes.",
            "format": "int64"
          }
        },
        "additionalProperties": false,
        "description": "A public media image."
      },
      "MovementDirection": {
        "enum": [
          "redemption",
          "award",
          "any"
        ],
        "type": "string",
        "description": "Which movements on a benefit-template-issued benefit an Neo.Runtime.Scheduler.Configuration.BenefitRedeemedSettings trigger reacts to."
      },
      "MovementResponse": {
        "type": "object",
        "properties": {
          "movementId": {
            "type": "string",
            "description": "Server-generated id of the movement, as listed in the benefit's `data.movements`."
          }
        },
        "additionalProperties": false,
        "description": "Response payload after a movement is created."
      },
      "MultipleUpdatePassData": {
        "type": "object",
        "allOf": [
          {
            "description": "Changes to apply to an existing pass, with options.",
            "$ref": "#/components/schemas/UpdatePassData_MultipleUpdatePassDataOptions"
          }
        ],
        "additionalProperties": false,
        "description": "Changes applied to every pass a bulk update matches. Omitted fields are left as they are on each pass."
      },
      "MultipleUpdatePassDataOptions": {
        "type": "object",
        "allOf": [
          {
            "$ref": "#/components/schemas/UpdatePassDataOptions"
          }
        ],
        "properties": {
          "throughput": {
            "type": "number",
            "description": "Passes updated per second. Must be greater than 0. Default 12, at most 1000; a value below 1 spaces\npasses more than a second apart. Best effort.",
            "format": "float"
          }
        },
        "additionalProperties": false,
        "description": "Options for a bulk update. Metadata is recomputed unless `updateMetadata` is `false`."
      },
      "NewProfile": {
        "type": "object",
        "properties": {
          "profileId": {
            "type": "integer",
            "description": "Actito identifier of the profile.",
            "format": "int64"
          }
        },
        "additionalProperties": false,
        "description": "The profile a profile webhook is about."
      },
      "NfcSettings": {
        "type": "object",
        "properties": {
          "apple": {
            "description": "Apple Wallet (Value Added Services) keys.",
            "$ref": "#/components/schemas/AppleNfcSettings"
          },
          "google": {
            "description": "Google Wallet (Smart Tap) keys.",
            "$ref": "#/components/schemas/GoogleNfcSettings"
          }
        },
        "additionalProperties": false,
        "description": "Keys a device needs to read wallet passes over NFC."
      },
      "NotifyRequest": {
        "type": "object",
        "properties": {
          "content": {
            "type": [
              "null",
              "string"
            ],
            "description": "Message shown on devices whose language has no entry in `localizedContent`. Optional when\n`localizedContent` has text; it then defaults to the tenant's default language entry, or else\nthe first language in ordinal order."
          },
          "localizedContent": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "string"
            },
            "description": "Message per device language. Keys are a lowercase ISO 639-1 code, optionally with an uppercase\nregion (`en`, `fr-FR`). Entries with blank text are not sent.",
            "propertyNames": {
              "pattern": "^[a-z]{2}(-[A-Z]{2})?$"
            }
          },
          "options": {
            "description": "Delivery options. Omitted, the notification is queued without refreshing pass data.",
            "$ref": "#/components/schemas/NotifyRequestOptions"
          }
        },
        "additionalProperties": false,
        "description": "The message to show the holder, in one or several languages."
      },
      "NotifyRequestOptions": {
        "type": "object",
        "properties": {
          "updateData": {
            "type": "boolean",
            "description": "Also refreshes the Google Wallet pass content in the same update as the message. Apple always\nrefreshes the whole pass to show a message, so this changes nothing there.",
            "default": false
          },
          "correlationId": {
            "maxLength": 100,
            "minLength": 10,
            "type": [
              "null",
              "string"
            ],
            "description": "Caller-chosen id attached to this notification for tracing, for example the campaign or batch it\nbelongs to."
          },
          "bypassQueue": {
            "type": "boolean",
            "description": "Sends the notification within the request (200) instead of queuing it (202). Use it only for urgent,\nlow-volume messages.",
            "default": false
          }
        },
        "additionalProperties": false,
        "description": "How the notification is delivered."
      },
      "OptionsRequest": {
        "type": "object",
        "properties": {
          "expiresOn": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "From this instant the value is no longer read; `null` keeps it readable indefinitely. Send it with a `Z` or an offset. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "notBefore": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "Until this instant the value is not read, and the previous value of the key, if still valid, is returned instead; `null` makes it readable at once. Same time zone rule as ExpiresOn. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          }
        },
        "additionalProperties": false,
        "description": "Window during which the stored value can be read. Both bounds are optional; when both are set,\n`notBefore` must be earlier than `expiresOn`."
      },
      "OrderChangeRequest": {
        "required": [
          "lastUpdate",
          "orderSecretToken",
          "state"
        ],
        "type": "object",
        "properties": {
          "ticketId": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Secutix ticket concerned by the change.",
            "format": "int64"
          },
          "saleMovementId": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Secutix sale movement (one ticket line of the order) concerned by the change. Its pass is the one\nupdated. Omitted, the passes of all movements and contacts of the order identified by\n`orderSecretToken` are updated.",
            "format": "int64"
          },
          "orderSecretToken": {
            "type": "string",
            "description": "Secret token of the Secutix order. Required and non-empty, otherwise 400."
          },
          "state": {
            "type": "string",
            "description": "Order state as reported by Secutix. Carried in the `Secutix:Order:Updated` event."
          },
          "lastUpdate": {
            "type": "string",
            "description": "Time of the change, as Secutix formats it."
          }
        },
        "additionalProperties": false,
        "description": "Order change notification, as Secutix sends it."
      },
      "OrderConfirmedData": {
        "type": "object",
        "properties": {
          "identifier": {
            "type": "string",
            "description": "Yurplan identifier of the order, carried as the order id of the\n            `Yurplan:Webhook:OrderValidated` event."
          },
          "tickets": {
            "type": "array",
            "items": {
              "description": "A Yurplan ticket.",
              "$ref": "#/components/schemas/TicketData"
            },
            "description": "Tickets of the order: one pass is created per ticket, an empty list creates none."
          }
        },
        "additionalProperties": false,
        "description": "Payload of an order confirmation."
      },
      "Pass": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Pass id: a 16-character string assigned at creation, unless the creator set it through a `neo.id` identifier. Also the Apple serial number and the suffix of the Google object id."
          },
          "secret": {
            "type": "string",
            "description": "Secret of the pass, used by the holder's wallet to receive pass updates. Assigned at creation unless set through `additionalData.neo.secret`; treat as confidential."
          },
          "creationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the pass was issued, UTC. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "lastUpdateDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the pass content last changed, UTC; equals `creationDate` when it never has. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "passType": {
            "type": "string",
            "description": "Pass template the pass renders from."
          },
          "identifiers": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            },
            "description": "Identifiers of the holder in other systems, keyed by system and field (`shopify.customerId`)."
          },
          "metadata": {
            "type": "object",
            "additionalProperties": {
              "type": "null"
            },
            "description": "Fields computed from the pass by the tenant's metadata configuration, used by filters and sorts. Datetime values are ISO 8601 strings."
          },
          "additionalData": {
            "type": "object",
            "additionalProperties": {
              "type": "null"
            },
            "description": "Free data stored with the pass by its creator and updates."
          },
          "providers": {
            "type": "object",
            "additionalProperties": { },
            "description": "Wallets the pass is installed on. `apple` (present while at least one Apple device is registered): `installationDate` of the first registered device and the `devices`. `google` (present while saved in Google Wallet): `installationDate`."
          },
          "themeId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Theme applied to the pass. `null` when the pass renders from its pass template alone."
          }
        },
        "additionalProperties": false,
        "description": "A pass as listed by `GET /passes`."
      },
      "PassCertificateDefinition": {
        "required": [
          "certificate",
          "hasKey"
        ],
        "type": "object",
        "properties": {
          "certificate": {
            "type": "string",
            "description": "Pass Type ID certificate issued by Apple, PEM-encoded. Public, so returned in clear."
          },
          "hasKey": {
            "type": "boolean",
            "description": "Whether the certificate's private key is set. Without it, no Apple pass can be signed."
          }
        },
        "additionalProperties": false,
        "description": "Apple Wallet pass signing certificate, with private key material redacted."
      },
      "PassCertificateRequest": {
        "required": [
          "certificate"
        ],
        "type": "object",
        "properties": {
          "key": {
            "type": [
              "null",
              "string"
            ],
            "description": "PEM-encoded private key of the certificate. Omit or leave empty to keep the current key; required\nthe first time Apple Wallet is configured."
          },
          "certificate": {
            "minLength": 1,
            "type": "string",
            "description": "Pass Type ID certificate issued by Apple, PEM-encoded."
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure the Apple Wallet pass signing certificate."
      },
      "PassCertificateSigningRequestDefinition": {
        "required": [
          "hasKey",
          "passTypeIdentifier"
        ],
        "type": "object",
        "properties": {
          "certificateRequest": {
            "type": [
              "null",
              "string"
            ],
            "description": "PEM-encoded certificate signing request to submit to Apple. Null when none was stored."
          },
          "passTypeIdentifier": {
            "type": "string",
            "description": "Pass type identifier the request is for, e.g. `pass.com.brand.loyalty`."
          },
          "hasKey": {
            "type": "boolean",
            "description": "Whether the private key the request was generated from is set."
          }
        },
        "additionalProperties": false,
        "description": "Current certificate signing request (CSR), with private key material redacted."
      },
      "PassCertificateSigningRequestRequest": {
        "required": [
          "passTypeIdentifier"
        ],
        "type": "object",
        "properties": {
          "key": {
            "type": [
              "null",
              "string"
            ],
            "description": "PEM-encoded private key the request was generated from. Omit or leave empty to keep the stored one;\nrequired when no certificate request is stored yet."
          },
          "certificateRequest": {
            "type": [
              "null",
              "string"
            ],
            "description": "PEM-encoded certificate signing request to submit to Apple."
          },
          "passTypeIdentifier": {
            "minLength": 1,
            "type": "string",
            "description": "Pass type identifier the request is for."
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure a certificate signing request (CSR)."
      },
      "PassConnectResponse": {
        "type": "object",
        "properties": {
          "url": {
            "type": "string",
            "description": "WebSocket URL for the pass, carrying an expiring access token: request a new one to reconnect."
          }
        },
        "additionalProperties": false,
        "description": "Where to listen for live changes of one pass."
      },
      "PassData": {
        "type": "object",
        "properties": {
          "identifiers": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            },
            "description": "Identifiers of the holder in other systems, keyed by system and field (`y2.customerId`,\n`shopify.customerId`). They are what `findPass`, `id.{key}` lookups and filters\nmatch on. Avoid keys starting with `id.`, the prefix lookups use."
          },
          "additionalData": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "null"
            },
            "description": "Free data stored with the pass and available to its templates (for example loyalty tier, store\ncode, campaign flags)."
          },
          "themeId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Theme applied to the pass, overriding the look of its pass template. Omit or send `null` to\nleave the current theme untouched (none on create); send an empty string to remove it. An id no\ndeclared theme has is refused with a 400."
          }
        },
        "additionalProperties": false,
        "description": "Fields a caller can set on a pass, at creation or on update."
      },
      "PassDefinition": {
        "required": [
          "certificate",
          "passTypeIdentifier"
        ],
        "type": "object",
        "properties": {
          "passTypeIdentifier": {
            "type": "string",
            "description": "Pass type identifier registered with Apple, e.g. `pass.com.brand.loyalty`, written into every Apple pass."
          },
          "certificate": {
            "description": "Certificate every Apple pass is signed with.",
            "$ref": "#/components/schemas/PassCertificateDefinition"
          },
          "certificateRequest": {
            "description": "Certificate request awaiting Apple's certificate, used to renew it. Null when none is stored.",
            "$ref": "#/components/schemas/PassCertificateSigningRequestDefinition"
          }
        },
        "additionalProperties": false,
        "description": "Pass configuration, with private key material redacted."
      },
      "PassDesktopQrCodeTranslations": {
        "type": "object",
        "properties": {
          "caption": {
            "type": [
              "null",
              "string"
            ],
            "description": "Instruction above the QR code."
          },
          "passDescription": {
            "type": [
              "null",
              "string"
            ],
            "description": "Text describing what scanning the QR code does."
          },
          "baseline": {
            "type": [
              "null",
              "string"
            ],
            "description": "Supporting text under the QR code."
          }
        },
        "additionalProperties": false,
        "description": "Strings around the QR code on a `pass` page opened on a desktop browser."
      },
      "PassDesktopTranslations": {
        "type": "object",
        "properties": {
          "qrCode": {
            "description": "Strings around the QR code the customer scans with their phone.",
            "$ref": "#/components/schemas/PassDesktopQrCodeTranslations"
          },
          "needHelpButton": {
            "type": [
              "null",
              "string"
            ],
            "description": "Label of the button opening the scanning help."
          },
          "needHelpDialog": {
            "description": "Strings of the scanning help dialog.",
            "$ref": "#/components/schemas/PassNeedHelpDialogTranslations"
          }
        },
        "additionalProperties": false,
        "description": "Strings shown on a `pass` page opened on a desktop browser."
      },
      "PassImageSlot": {
        "enum": [
          "appleStrip",
          "appleArtwork",
          "appleBackground",
          "appleThumbnail",
          "appleLogo",
          "appleIcon",
          "applePrimaryLogo",
          "appleSecondaryLogo",
          "googleHero",
          "googleLogo",
          "googleWideLogo",
          "googleProgramLogo",
          "googleWideProgramLogo",
          "googleTitleImage",
          "googleWideTitleImage"
        ],
        "type": "string",
        "description": "An image position on a wallet pass that an appearance source (a theme, for example) can override."
      },
      "PassInstalledCondition": {
        "enum": [
          "firstInstallationOnly",
          "anyInstallation"
        ],
        "type": "string",
        "description": "Controls when a Neo.Runtime.Scheduler.Configuration.PassInstalledSettings trigger fires relative to installs."
      },
      "PassListLayoutTranslations": {
        "type": "object",
        "properties": {
          "title": {
            "type": [
              "null",
              "string"
            ],
            "description": "Headline used for two or more passes."
          },
          "title_one": {
            "type": [
              "null",
              "string"
            ],
            "description": "Headline used for exactly one pass."
          },
          "title_zero": {
            "type": [
              "null",
              "string"
            ],
            "description": "Headline used when the customer holds no pass."
          },
          "subTitle": {
            "type": [
              "null",
              "string"
            ],
            "description": "Text under the headline."
          },
          "subTitle_zero": {
            "type": [
              "null",
              "string"
            ],
            "description": "Text under the headline when the customer holds no pass."
          },
          "individual": {
            "type": [
              "null",
              "string"
            ],
            "description": "Label of the individual-passes section, for two or more."
          },
          "individual_one": {
            "type": [
              "null",
              "string"
            ],
            "description": "Label of the individual-passes section, for exactly one."
          },
          "all": {
            "type": [
              "null",
              "string"
            ],
            "description": "Label of the all-passes action, for two or more."
          },
          "all_one": {
            "type": [
              "null",
              "string"
            ],
            "description": "Label of the all-passes action, for exactly one."
          },
          "tickets": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass counter. Carries a `{count}` placeholder."
          }
        },
        "additionalProperties": false,
        "description": "Headline strings of a `passList` page."
      },
      "PassListQrCodeTranslations": {
        "type": "object",
        "properties": {
          "seeQRCode": {
            "type": [
              "null",
              "string"
            ],
            "description": "Label of the action revealing the QR code."
          },
          "scanQRCode": {
            "type": [
              "null",
              "string"
            ],
            "description": "Title shown with the QR code."
          },
          "QRCodeInstructions": {
            "type": [
              "null",
              "string"
            ],
            "description": "Scanning instructions. May be HTML, prefixed with `$html`."
          },
          "copyQRLink": {
            "type": [
              "null",
              "string"
            ],
            "description": "Label of the action copying the QR code link."
          },
          "linkCopied": {
            "type": [
              "null",
              "string"
            ],
            "description": "Confirmation shown once the link has been copied."
          }
        },
        "additionalProperties": false,
        "description": "Strings around the QR code on a `passList` page."
      },
      "PassMobileTranslations": {
        "type": "object",
        "properties": {
          "title": {
            "type": [
              "null",
              "string"
            ],
            "description": "Headline of the page."
          },
          "subTitle": {
            "type": [
              "null",
              "string"
            ],
            "description": "Text under the headline. May be HTML, prefixed with `$html`."
          },
          "postInstalled": {
            "description": "Strings shown once the pass has been added to the wallet.",
            "$ref": "#/components/schemas/PassPostInstalledTranslations"
          }
        },
        "additionalProperties": false,
        "description": "Strings shown on a `pass` page opened on a phone."
      },
      "PassNeedHelpDialogTranslations": {
        "type": "object",
        "properties": {
          "title": {
            "type": [
              "null",
              "string"
            ],
            "description": "Title of the dialog."
          },
          "closeButton": {
            "type": [
              "null",
              "string"
            ],
            "description": "Label of the button closing the dialog."
          }
        },
        "additionalProperties": false,
        "description": "Strings of the scanning help dialog on a `pass` page."
      },
      "PassPostInstalledTranslations": {
        "type": "object",
        "properties": {
          "title": {
            "type": [
              "null",
              "string"
            ],
            "description": "Headline of the confirmation."
          },
          "description": {
            "type": [
              "null",
              "string"
            ],
            "description": "Text under the confirmation headline."
          },
          "viewMyCard": {
            "type": [
              "null",
              "string"
            ],
            "description": "Label of the button opening the installed pass."
          }
        },
        "additionalProperties": false,
        "description": "Strings shown on a `pass` page once the pass has been installed."
      },
      "PassRequest": {
        "required": [
          "certificate",
          "passTypeIdentifier"
        ],
        "type": "object",
        "properties": {
          "passTypeIdentifier": {
            "minLength": 1,
            "type": "string",
            "description": "Pass type identifier registered with Apple, e.g. `pass.com.brand.loyalty`."
          },
          "certificate": {
            "description": "Certificate Apple passes are signed with.",
            "$ref": "#/components/schemas/PassCertificateRequest"
          },
          "certificateRequest": {
            "description": "Certificate request awaiting Apple's certificate. Omitted or null removes the stored request, so send\nit back while a renewal is pending.",
            "$ref": "#/components/schemas/PassCertificateSigningRequestRequest"
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure the Apple Wallet pass."
      },
      "PassStatistic": {
        "type": "object",
        "properties": {
          "count": {
            "description": "Issued and installed pass counts.",
            "$ref": "#/components/schemas/PassStatisticCount"
          }
        },
        "additionalProperties": false,
        "description": "Pass statistics for the tenant, or for one pass template."
      },
      "PassStatisticCount": {
        "type": "object",
        "properties": {
          "total": {
            "type": "integer",
            "description": "Passes issued, installed or not.",
            "format": "int32"
          },
          "active": {
            "type": "integer",
            "description": "Passes installed on at least one device, in either wallet.",
            "format": "int32"
          },
          "apple": {
            "type": "integer",
            "description": "Passes registered on at least one Apple device right now.",
            "format": "int32"
          },
          "google": {
            "type": "integer",
            "description": "Passes currently saved in Google Wallet.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "Pass counts at the time of the request. A pass installed on both wallets counts once in\n`active` and once in each of `apple` and `google`."
      },
      "PassTheme": {
        "required": [
          "id",
          "name"
        ],
        "type": "object",
        "properties": {
          "id": {
            "maxLength": 64,
            "minLength": 0,
            "pattern": "^[a-zA-Z0-9][a-zA-Z0-9_-]{0,63}$",
            "type": "string",
            "description": "Stable, URL-safe identifier (for example `summer-2026`): 1 to 64 letters, digits, `-` or\n`_`, starting with a letter or a digit, case-sensitive. Cannot be changed after creation:\npasses reference it and the theme's image paths contain it."
          },
          "name": {
            "maxLength": 200,
            "minLength": 0,
            "type": "string",
            "description": "Display name shown in the admin interface and in the pass theme picker. At most 200 characters."
          },
          "tags": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Free-form labels used to filter and group themes in the admin. At most 20 tags of 50 characters; each\nis trimmed, blank ones are dropped and a tag repeated in another casing is kept once."
          },
          "appearance": {
            "description": "Colors and images laid over the pass template. `null` keeps the pass template's appearance.",
            "$ref": "#/components/schemas/PassThemeAppearance"
          },
          "content": {
            "description": "Localized text the pass template can show to the holder. `null` when the theme has none.",
            "$ref": "#/components/schemas/PassThemeContent"
          },
          "creationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the theme was created, in UTC. Set by the server; ignored on write. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "lastModificationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the theme was last created or updated, in UTC. Set by the server; ignored on write. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          }
        },
        "additionalProperties": false,
        "description": "API representation of a theme — a reusable visual skin applied over a pass template for a season or\na campaign."
      },
      "PassThemeAppearance": {
        "type": "object",
        "properties": {
          "backgroundColor": {
            "pattern": "^(#([0-9a-fA-F]{3}|[0-9a-fA-F]{6})|rgb\\(\\s*\\d{1,3}\\s*,\\s*\\d{1,3}\\s*,\\s*\\d{1,3}\\s*\\))$",
            "type": [
              "null",
              "string"
            ],
            "description": "Card background color, as `#RRGGBB`, `#RGB` or `rgb(r, g, b)` with channels from 0 to\n255. Returned as `#RRGGBB` (`#FF7A52`). Empty keeps the pass template's color."
          },
          "foregroundColor": {
            "pattern": "^(#([0-9a-fA-F]{3}|[0-9a-fA-F]{6})|rgb\\(\\s*\\d{1,3}\\s*,\\s*\\d{1,3}\\s*,\\s*\\d{1,3}\\s*\\))$",
            "type": [
              "null",
              "string"
            ],
            "description": "Color of the field values. Same notations as `backgroundColor`; empty keeps the pass\ntemplate's color."
          },
          "labelColor": {
            "pattern": "^(#([0-9a-fA-F]{3}|[0-9a-fA-F]{6})|rgb\\(\\s*\\d{1,3}\\s*,\\s*\\d{1,3}\\s*,\\s*\\d{1,3}\\s*\\))$",
            "type": [
              "null",
              "string"
            ],
            "description": "Color of the field labels, on Apple Wallet only. Same notations as `backgroundColor`; empty keeps\nthe pass template's color."
          },
          "mainImageUrl": {
            "description": "The theme's default image. Used by the banner slot of each platform when it carries no override\nof its own — the Apple strip and the Google hero. Everything else, Apple's other large slots\nincluded, is only set through Neo.Web.Api.Theme.Controllers.ThemeController.PassThemeAppearance.Images.",
            "$ref": "#/components/schemas/PassThemeLocalizedString"
          },
          "images": {
            "type": "array",
            "items": {
              "description": "One image override within a theme appearance.",
              "$ref": "#/components/schemas/PassThemeImage"
            },
            "description": "Per-slot image overrides. At most one entry per Neo.Runtime.Wallet.Appearance.PassImageSlot: a second entry for the\nsame slot is refused with a 400."
          }
        },
        "additionalProperties": false,
        "description": "Colors and images of a theme. Anything left empty keeps the pass template's own value."
      },
      "PassThemeContent": {
        "type": "object",
        "properties": {
          "title": {
            "description": "Theme title. Reachable from a pass template as `{{ theme.title }}`.",
            "$ref": "#/components/schemas/PassThemeLocalizedString"
          },
          "description": {
            "description": "Theme description. Reachable from a pass template as `{{ theme.description }}`.",
            "$ref": "#/components/schemas/PassThemeLocalizedString"
          }
        },
        "additionalProperties": false,
        "description": "Localized text of a theme, shown on the pass."
      },
      "PassThemeImage": {
        "required": [
          "slot",
          "url"
        ],
        "type": "object",
        "properties": {
          "slot": {
            "description": "Which image on which platform this entry replaces.",
            "$ref": "#/components/schemas/PassImageSlot"
          },
          "url": {
            "description": "Image location: an absolute `https://` URL, or the `path` of an image already uploaded to\nthis theme (`public/themes/summer-2026/apple-strip.png`). Anything else, including another\ntheme's image or one not uploaded yet, is refused with a 400.",
            "$ref": "#/components/schemas/PassThemeLocalizedString"
          }
        },
        "additionalProperties": false,
        "description": "One image override within a theme appearance."
      },
      "PassThemeLocalizedString": {
        "required": [
          "default"
        ],
        "type": "object",
        "properties": {
          "default": {
            "minLength": 1,
            "type": "string",
            "description": "Value used when no localization matches the requested language."
          },
          "localizations": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "string"
            },
            "description": "Per-language overrides keyed by language code (`fr`, `fr-FR`). Each key must be one of the\ntenant's available languages (compared ignoring case), or the theme is refused with a 400. For images\nthese are honoured on Apple Wallet only — Google Wallet takes a single image per slot and always\nreceives Neo.Web.Api.Theme.Controllers.ThemeController.PassThemeLocalizedString.Default."
          }
        },
        "additionalProperties": false,
        "description": "A value with a mandatory default and optional per-language overrides."
      },
      "PassTypeAppearance": {
        "type": "object",
        "properties": {
          "background": {
            "type": [
              "null",
              "string"
            ],
            "description": "The card's background, as configured — `rgb(...)` or `#rrggbb`."
          },
          "foreground": {
            "type": [
              "null",
              "string"
            ],
            "description": "The colour field values are drawn in."
          },
          "label": {
            "type": [
              "null",
              "string"
            ],
            "description": "The colour field labels are drawn in."
          }
        },
        "additionalProperties": false,
        "description": "The colours a pass is drawn in, which is what tells two templates apart at a glance."
      },
      "PassTypeApple": {
        "type": "object",
        "properties": {
          "actionLinks": {
            "description": "Configuration for action links associated with the pass.",
            "$ref": "#/components/schemas/PassTypeAppleActionLinks"
          },
          "additionalInfoFields": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Information about a field.",
              "$ref": "#/components/schemas/PassTypeAppleField"
            },
            "description": "Fields displayed in the Additional Info section below the pass content. Used for poster event ticket\npasses (iOS 18+)."
          },
          "appLaunchUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "A URL the system passes to the associated app from associatedStoreIdentifiers during launch. The app\nreceives this URL in the application(_:didFinishLaunchingWithOptions:) and\napplication(_:open:options:) methods of its app delegate. This key isn't supported for watchOS."
          },
          "associatedStoreIdentifiers": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "integer",
              "format": "int64"
            },
            "description": "An array of App Store identifiers for apps associated with the pass. The associated app on a device\nis the first item in the array that's compatible with that device. A link to launch the app is on\nthe back of the pass.If the app isn't installed, the link opens the App Store. This key works only\nfor payment passes. This key isn't supported for watchOS."
          },
          "auxiliaryFields": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Information about a field.",
              "$ref": "#/components/schemas/PassTypeAppleField"
            },
            "description": "Additional fields to be displayed on the front of the pass."
          },
          "auxiliaryStoreIdentifiers": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "integer",
              "format": "int64"
            },
            "description": "Additional App Store identifiers for apps associated with the pass. A link to launch the app is in\nthe event guide of the pass. This key works only for poster event tickets. This key isn't supported\nfor watchOS."
          },
          "backFields": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Information about a field.",
              "$ref": "#/components/schemas/PassTypeAppleField"
            },
            "description": "Fields to be on the back of the pass."
          },
          "backgroundColor": {
            "type": [
              "null",
              "string"
            ],
            "description": "Background color of the pass, specified as an CSS-style RGB triple."
          },
          "barCodeAlternateText": {
            "type": [
              "null",
              "string"
            ],
            "description": "Text displayed near the barcode. For example, a human-readable version of the barcode data in case\nthe barcode doesn't scan. A Liquid template, not a translatable string: one value for every\nlanguage."
          },
          "barCodeFormat": {
            "type": [
              "null",
              "string"
            ],
            "description": "Bar code format. One of: QR, PDF417, Aztec, Code128, Code39, Codabar, EAN13, I2of5. Code39, Codabar,\nEAN13 and I2of5 need iOS 27; the pass also carries a QR code of the same value for older devices.\nNo bar code is drawn when `barCodeValue` renders empty."
          },
          "barCodeValue": {
            "type": [
              "null",
              "string"
            ],
            "description": "Bar code field value (ex: `id.y2.customerId`)."
          },
          "beacons": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Configuration for a beacon device",
              "$ref": "#/components/schemas/PassTypeAppleBeacon"
            },
            "description": "Beacons marking locations where the pass is relevant. You can't add more than 10 beacons."
          },
          "description": {
            "description": "A simple description of the pass This string is localizable. Shown to the pass holder, so it carries\none value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "eventLogoText": {
            "description": "The text to display next to the logo on the pass. Used exclusively for posterEventTickets, takes\nprecedent over `logoText`. This string is localizable. Shown to the pass holder, so it carries one\nvalue per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "expirationDate": {
            "type": [
              "null",
              "string"
            ],
            "description": "Optional. Date and time when the pass expires. The value must be a complete date with hours and\nminutes, and may optionally include seconds."
          },
          "featuredActions": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "A featured action card displayed when viewing the pass in the Wallet app (iOS 18+). Each featured\naction includes an icon, a predefined action type, and a URL.",
              "$ref": "#/components/schemas/PassTypeAppleFeaturedAction"
            },
            "description": "Featured actions displayed below the pass in Wallet (iOS 27+). Maximum 2 entries."
          },
          "footerBackgroundColor": {
            "type": [
              "null",
              "string"
            ],
            "description": "A background color for the footer of the pass, specified as a CSS-style RGB triple, such as rgb(100,\n10, 110). This key works only for poster event tickets."
          },
          "footerFields": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Information about a field.",
              "$ref": "#/components/schemas/PassTypeAppleField"
            },
            "description": "Fields displayed in the footer of the pass. Used for poster layouts (iOS 27+)."
          },
          "foregroundColor": {
            "type": [
              "null",
              "string"
            ],
            "description": "Foreground color of the pass, specified as a CSS-style RGB triple."
          },
          "groupingIdentifier": {
            "type": [
              "null",
              "string"
            ],
            "description": "An identifier the system uses to group related boarding passes or event tickets. Wallet displays\npasses with the same groupingIdentifier, passTypeIdentifier, and type as a group. Use this\nidentifier to group passes that are tightly related, such as boarding passes for different\nconnections on the same trip."
          },
          "headerFields": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Information about a field.",
              "$ref": "#/components/schemas/PassTypeAppleField"
            },
            "description": "Fields to be displayed in the header on the front of the pass. Use header fields sparingly; unlike\nall other fields, they remain visible when a stack of passes are displayed."
          },
          "images": {
            "description": "Configuration of image for this pass.",
            "$ref": "#/components/schemas/PassTypeAppleImage"
          },
          "labelColor": {
            "type": [
              "null",
              "string"
            ],
            "description": "Color of the label text, specified as a CSS-style RGB triple."
          },
          "locations": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Configuration for a location",
              "$ref": "#/components/schemas/PassTypeAppleLocation"
            },
            "description": "Locations where the pass is relevant. For example, the location of your store. You can't add more\nthan 10 locations."
          },
          "logoText": {
            "description": "Text displayed next to the logo on the pass. This string is localizable. Shown to the pass holder,\nso it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "maxDistance": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Maximum distance in meters from a relevant latitude and longitude that the pass is relevant. This\nnumber is compared to the pass's default distance and the smaller value is used.",
            "format": "int32"
          },
          "nfc": {
            "description": "NFC-enabled pass keys support sending reward card information as part of an Apple Pay transaction.",
            "$ref": "#/components/schemas/PassTypeAppleNfc"
          },
          "organizationName": {
            "type": [
              "null",
              "string"
            ],
            "description": "Display name of the organization that originated and signed the pass. This string is localizable."
          },
          "primaryFields": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Information about a field.",
              "$ref": "#/components/schemas/PassTypeAppleField"
            },
            "description": "Fields to be displayed prominently on the front of the pass."
          },
          "relevantDate": {
            "type": [
              "null",
              "string"
            ],
            "description": "Recommended for event tickets and boarding passes; otherwise optional. Date and time when the pass\nbecomes relevant. For example, the start time of a movie. The value must be a complete date with\nhours and minutes, and may optionally include seconds."
          },
          "relevantDates": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Configuration for a relevantDates entry. Use `StartDate` alone (no `EndDate`) to let\nWallet auto-calculate the interval, or supply both to define an explicit interval.",
              "$ref": "#/components/schemas/PassTypeAppleRelevantDate"
            },
            "description": "An array of date intervals during which the pass is relevant. Supersedes `RelevantDate` when\nnon-empty."
          },
          "secondaryFields": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Information about a field.",
              "$ref": "#/components/schemas/PassTypeAppleField"
            },
            "description": "Fields to be displayed on the front of the pass."
          },
          "semantics": {
            "description": "Semantics configuration for the pass.",
            "$ref": "#/components/schemas/PassTypeAppleSemantics"
          },
          "sharingProhibited": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Disables sharing of the pass."
          },
          "summaryFields": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Information about a field.",
              "$ref": "#/components/schemas/PassTypeAppleField"
            },
            "description": "Up to three values displayed below the barcode on the poster generic layout (iOS 27+). The poster\nlayout and the classic layout show a different number of fields, in a different place and with a\ndifferent typography, so they are edited separately: `PrimaryFields` stays classic-only."
          },
          "suppressHeaderDarkening": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "A Boolean value that controls whether to display the header darkening gradient on poster event\ntickets. The default value is false. This key works only for poster event tickets."
          },
          "suppressStripShine": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "A Boolean value that controls whether to display the strip image without a shine effect. The default\nvalue is true."
          },
          "type": {
            "type": [
              "null",
              "string"
            ],
            "description": "Type of pass. One of: Generic, BoardingPass, Coupon, EventTicket, StoreCard."
          },
          "upcomingPassInformation": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Part of the Apple configuration.",
              "$ref": "#/components/schemas/PassTypeAppleUpcomingPassInformation"
            },
            "description": "Further events the ticket admits to, each shown as its own entry in the event guide."
          },
          "useAutomaticColors": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "A Boolean value that controls whether Wallet computes the foreground and label color that the pass\nuses. The system derives the background color from the background image of the pass. This key works\nonly for poster event tickets. This key ignores the values that foregroundColor and labelColor\nspecify."
          },
          "usePosterLayout": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "When true, a customer card pass uses the iOS 27+ poster generic layout instead of the standard store\ncard layout."
          },
          "voided": {
            "type": [
              "null",
              "string"
            ],
            "description": "Optional. Indicates that the pass is void'for example, a one time use coupon that has been redeemed."
          }
        },
        "additionalProperties": false,
        "description": "Configuration of an apple pass. See [Apple official\ndocumentation](https://developer.apple.com/library/archive/documentation/UserExperience/Reference/PassKit_Bundle/Chapters/TopLevel.html#//apple_ref/doc/uid/TP40012026-CH2-SW1)\nfor more information"
      },
      "PassTypeAppleActionLinks": {
        "type": "object",
        "properties": {
          "accessibilityURL": {
            "type": [
              "null",
              "string"
            ],
            "description": "A URL that links to your accessiblity content, or the venue's. This key works only for poster event\ntickets."
          },
          "addOnURL": {
            "type": [
              "null",
              "string"
            ],
            "description": "A URL that can link to experiences that someone can add to the pass. This key works only for poster\nevent tickets."
          },
          "bagPolicyURL": {
            "type": [
              "null",
              "string"
            ],
            "description": "A URL that links to the bag policy of the venue for the event that the pass represents. This key\nworks only for poster event tickets."
          },
          "contactVenueEmail": {
            "type": [
              "null",
              "string"
            ],
            "description": "The preferred email address to contact the venue, event, or issuer. This key works only for poster\nevent tickets."
          },
          "contactVenuePhoneNumber": {
            "type": [
              "null",
              "string"
            ],
            "description": "The phone number for contacting the venue, event, or issuer. This key works only for poster event\ntickets."
          },
          "contactVenueWebsite": {
            "type": [
              "null",
              "string"
            ],
            "description": "A URL that links to the website of the venue, event, or issuer. This key works only for poster event\ntickets."
          },
          "directionsInformationURL": {
            "type": [
              "null",
              "string"
            ],
            "description": "A URL that links to directions for the event. This key works only for poster event tickets."
          },
          "merchandiseURL": {
            "type": [
              "null",
              "string"
            ],
            "description": "A URL that links to a site for ordering merchandise for the event that the pass represents. This key\nworks only for poster event tickets."
          },
          "orderFoodURL": {
            "type": [
              "null",
              "string"
            ],
            "description": "A URL that links to the food ordering page for the event that the pass represents. This key works\nonly for poster event tickets."
          },
          "parkingInformationURL": {
            "type": [
              "null",
              "string"
            ],
            "description": "A URL that links to parking information for the event that the pass represents. This key works only\nfor poster event tickets."
          },
          "purchaseParkingURL": {
            "type": [
              "null",
              "string"
            ],
            "description": "A URL that links to a site to purchase parking for the event that the pass represents. This key\nworks only for poster event tickets."
          },
          "sellURL": {
            "type": [
              "null",
              "string"
            ],
            "description": "A URL that links to the selling flow for the ticket the pass represents. This key works only for\nposter event tickets."
          },
          "transferURL": {
            "type": [
              "null",
              "string"
            ],
            "description": "A URL that links to the transferring flow for the ticket that the pass represents. This key works\nonly for poster event tickets."
          },
          "transitInformationURL": {
            "type": [
              "null",
              "string"
            ],
            "description": "A URL that links to information about transit options in the area of the event that the pass\nrepresents. This key works only for poster event tickets."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Apple configuration."
      },
      "PassTypeAppleBeacon": {
        "type": "object",
        "properties": {
          "label": {
            "description": "Text displayed on the lock screen when the pass is currently relevant. For example, a description of\nthe nearby location such as 'Store nearby on 1st and Main.'. This string is localizable. Shown to\nthe pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "major": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Major identifier of a Bluetooth Low Energy location beacon.",
            "format": "int32"
          },
          "minor": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Minor identifier of a Bluetooth Low Energy location beacon.",
            "format": "int32"
          },
          "uuid": {
            "type": [
              "null",
              "string"
            ],
            "description": "Unique identifier of a Bluetooth Low Energy location beacon."
          }
        },
        "additionalProperties": false,
        "description": "Configuration for a beacon device"
      },
      "PassTypeAppleCurrencyAmount": {
        "type": "object",
        "properties": {
          "amount": {
            "type": [
              "null",
              "string"
            ],
            "description": "Amount in currency units."
          },
          "currencyCode": {
            "type": [
              "null",
              "string"
            ],
            "description": "Three-letter currency code (ISO 4217), e.g., \"USD\"."
          }
        },
        "additionalProperties": false,
        "description": "An object that represents an amount of money and type of currency. See\nSemanticTagType.CurrencyAmount."
      },
      "PassTypeAppleDateInformation": {
        "type": "object",
        "properties": {
          "date": {
            "type": [
              "null",
              "string"
            ],
            "description": "The start date of the upcoming pass information entry. If omitted, the entry lists the Time and Date\nas TBD."
          },
          "ignoreTimeComponents": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Indicates whether the entry should ignore the time components of the date."
          },
          "isAllDay": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Indicates whether the entry spans the entire day and that the time components should be ignored."
          },
          "isUnannounced": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Indicates whether the provided time of the event hasn't been announced (commonly referred to as\nTBA)."
          },
          "isUndetermined": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Indicates whether the provided time of the event hasn't been determined (commonly referred to as\nTBD)."
          },
          "timeZone": {
            "type": [
              "null",
              "string"
            ],
            "description": "The time zone to adjust the date into. If omitted, the entry uses the current time zone of the\ndevice."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Apple configuration."
      },
      "PassTypeAppleEventDateInfoValue": {
        "type": "object",
        "properties": {
          "date": {
            "type": [
              "null",
              "string"
            ],
            "description": "The date (ISO 8601 date as string)."
          },
          "ignoreTimeComponents": {
            "type": [
              "null",
              "string"
            ],
            "description": "A Boolean value that indicates whether the system ignores the time components of the date. Sent as a\nstring: `true`, `false` or a Liquid template."
          },
          "timeZone": {
            "type": [
              "null",
              "string"
            ],
            "description": "The time zone to display in the date. Uses IANA time zone database identifiers (e.g.\n\"America/Los_Angeles\")."
          },
          "unannounced": {
            "type": [
              "null",
              "string"
            ],
            "description": "A Boolean value that indicates whether the date of the event is announced. Sent as a string:\n`true`, `false` or a Liquid template."
          },
          "undetermined": {
            "type": [
              "null",
              "string"
            ],
            "description": "A Boolean value that indicates whether the date of the event is determined. Sent as a string:\n`true`, `false` or a Liquid template."
          }
        },
        "additionalProperties": false,
        "description": "An object that provides information for the date and time of an event. Source:\nSemanticTagType.EventDateInfo (iOS 18.0+, iPadOS 18.0+, watchOS 11.0+).\nhttps://developer.apple.com/documentation/walletpasses/semantictagtype/eventdateinfo-data.dictionary"
      },
      "PassTypeAppleFeaturedAction": {
        "type": "object",
        "properties": {
          "icon": {
            "type": [
              "null",
              "string"
            ],
            "description": "An SF Symbol name for the icon displayed on the featured action card. Prefer circular, filled\nvariants that clearly represent the action at a glance. If omitted, the system uses a default icon\nfor the action type."
          },
          "type": {
            "type": [
              "null",
              "string"
            ],
            "description": "The predefined action type that determines the label and behavior of the featured action card."
          },
          "url": {
            "type": [
              "null",
              "string"
            ],
            "description": "The URL to open when someone taps the featured action. The destination depends on the action type '\nfor example, a website, a deep link into your app, or a `tel:` URI for `call` actions."
          }
        },
        "additionalProperties": false,
        "description": "A featured action card displayed when viewing the pass in the Wallet app (iOS 18+). Each featured\naction includes an icon, a predefined action type, and a URL."
      },
      "PassTypeAppleField": {
        "type": "object",
        "properties": {
          "changeMessage": {
            "description": "Format string for the alert text that is displayed when the pass is updated. The format string must\ncontain the escape `%@`, which is replaced with the field's new value. For example, `Gate changed to\n%@.` If you don't specify a change message, the user isn't notified when the field changes. Shown to\nthe pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "key": {
            "type": [
              "null",
              "string"
            ],
            "description": "The key must be unique within the scope of the entire pass. For example, 'departure-gate.'."
          },
          "label": {
            "description": "Label text for the field. This string is localizable. Shown to the pass holder, so it carries one\nvalue per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "textAlignment": {
            "type": [
              "null",
              "string"
            ],
            "description": "Text alignment for the field. One of: Left, Center, Right, Natural."
          },
          "value": {
            "description": "Value of the field, for example, 42. The value may contain HTML markup for links.Only the >a<\ntag and its href attribute are supported.For example, the following is key-value pair specifies a\nlink with the text 'Edit my profile': \"value\": \" \" This key's value overrides the text specified by\nthe value key. Available in iOS 7.0. This string is localizable. Shown to the pass holder, so it\ncarries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          }
        },
        "additionalProperties": false,
        "description": "Information about a field."
      },
      "PassTypeAppleImage": {
        "type": "object",
        "properties": {
          "artWork": {
            "type": [
              "null",
              "string"
            ],
            "description": "Poster background image (artwork.png) used by both poster event tickets (iOS 18+) and poster generic\npasses (iOS 27+). Setting this on a generic pass automatically activates the posterGeneric layout;\non an event ticket it activates posterEventTicket. Falls back to the strip image on older devices.\n358x448 pts."
          },
          "background": {
            "type": [
              "null",
              "string"
            ],
            "description": "Blurred background image for non-poster event tickets (background.png). The image is displayed\nbehind the entire front of the pass and blurred by the system. The expected dimensions are 343 x 503\npoints. For poster event tickets and poster generic passes, use ArtWork instead."
          },
          "footer": {
            "type": [
              "null",
              "string"
            ],
            "description": "The image displayed on the front of the pass near the barcode. The allotted space is 858 x 45\npoints."
          },
          "icon": {
            "type": [
              "null",
              "string"
            ],
            "description": "The pass's icon. This is displayed in notifications and in emails that have a pass attached, and on\nthe lock screen. When it is displayed, the icon gets a shine effect and rounded corners. The icon\nshould measure 87 x 87 points."
          },
          "logo": {
            "type": [
              "null",
              "string"
            ],
            "description": "The image displayed on the front of the pass in the top left. The allotted space is 480 x 150\npoints; in most cases it should be narrower."
          },
          "primaryLogo": {
            "type": [
              "null",
              "string"
            ],
            "description": "Top-left logo for poster layouts (posterGeneric iOS 27+ and posterEventTicket iOS 18+). 126x30 pts."
          },
          "reuseExisting": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "For an upcoming event's header image or venue map: reuse the image the pass already carries rather\nthan download one. `urls` takes precedence when set."
          },
          "secondaryLogo": {
            "type": [
              "null",
              "string"
            ],
            "description": "Logo image that is displayed on bottom right footer inset of the pass. Ticket issuer or event\ncompany logo 135x12 pts."
          },
          "stampImages": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "The Apple images a stamp card shows at one exact stamp count.",
              "$ref": "#/components/schemas/PassTypeAppleStampImage"
            },
            "description": "Per-stamp-count overrides of `Strip` and `ArtWork`, for a stamp card."
          },
          "strip": {
            "type": [
              "null",
              "string"
            ],
            "description": "The image displayed behind the primary fields on the front of the pass. On iPhone 6 and 6 Plus The\nallotted space is 1125 x 296 points for event tickets, 1125 x 432 points for gift cards and coupons,\nand 1125 x 369 in all other cases. On prior hardware The allotted space is 960 x 252 points for\nevent tickets, 960 x 330 points for other pass styles with a square barcode on devices with 3.5 inch\nscreens, and 960 x 369 in all other cases."
          },
          "thumbnail": {
            "type": [
              "null",
              "string"
            ],
            "description": "An additional image displayed on the front of the pass. For example, on a membership card, the\nthumbnail could be used to a picture of the cardholder. The allotted space is 270 x 270 points. The\naspect ratio should be in the range of 2:3 to 3:2, otherwise the image is cropped."
          },
          "urls": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Part of the Apple configuration.",
              "$ref": "#/components/schemas/PassTypeAppleImageUrl"
            },
            "description": "For an upcoming event's header image or venue map: the remote copies of the image the device\ndownloads."
          },
          "venueMap": {
            "type": [
              "null",
              "string"
            ],
            "description": "Issuer-provided static map of the venue, which will be shown in the event guide."
          }
        },
        "additionalProperties": false,
        "description": "Image configuration for the pass"
      },
      "PassTypeAppleImageUrl": {
        "type": "object",
        "properties": {
          "scale": {
            "type": [
              "null",
              "number"
            ],
            "description": "The scale of the image. If unspecified, defaults to 1.",
            "format": "double"
          },
          "sha256": {
            "type": [
              "null",
              "string"
            ],
            "description": "(Required) The SHA256 hash of the image."
          },
          "size": {
            "type": [
              "null",
              "string"
            ],
            "description": "Size of the image asset in bytes. The maximum allowed size is 2 megabytes."
          },
          "url": {
            "type": [
              "null",
              "string"
            ],
            "description": "(Required) The URL that points to the image asset to be downloaded. This must be an https link."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Apple configuration."
      },
      "PassTypeAppleImages": {
        "type": "object",
        "properties": {
          "headerImage": {
            "description": "The name of the image file used for the header image on the details screen. This can be a remote\nasset.",
            "$ref": "#/components/schemas/PassTypeAppleImage"
          },
          "venueMap": {
            "description": "The name of the image file used for the venue map in the event guide for each upcoming pass\ninformation entry. This can be a remote asset and is available for event entries.",
            "$ref": "#/components/schemas/PassTypeAppleImage"
          }
        },
        "additionalProperties": false,
        "description": "Part of the Apple configuration."
      },
      "PassTypeAppleLocation": {
        "type": "object",
        "properties": {
          "altitude": {
            "type": [
              "null",
              "string"
            ],
            "description": "Altitude, in meters, of the location."
          },
          "label": {
            "description": "Text displayed on the lock screen when the pass is currently relevant. For example, a description of\nthe nearby location such as 'Store nearby on 1st and Main.' This string is localizable. Shown to the\npass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "latitude": {
            "type": [
              "null",
              "string"
            ],
            "description": "Latitude, in degrees, of the location."
          },
          "longitude": {
            "type": [
              "null",
              "string"
            ],
            "description": "Longitude, in degrees, of the location."
          }
        },
        "additionalProperties": false,
        "description": "Configuration for a location"
      },
      "PassTypeAppleNfc": {
        "type": "object",
        "properties": {
          "encryptionPublicKey": {
            "type": [
              "null",
              "string"
            ],
            "description": "The public encryption key used by the Value Added Services protocol. Use a Base64 encoded X.509\nSubjectPublicKeyInfo structure containing a ECDH public key for group P256."
          },
          "message": {
            "type": [
              "null",
              "string"
            ],
            "description": "The payload to be transmitted to the Apple Pay terminal. Must be 64 bytes or less. Messages longer\nthan 64 bytes are truncated by the system."
          },
          "requiresAuthentication": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "A Boolean value that indicates whether the NFC pass requires authentication. The default value is\nfalse. A value of true requires the user to authenticate for each use of the NFC pass."
          }
        },
        "additionalProperties": false,
        "description": "Information about the NFC payload passed to an Apple Pay terminal."
      },
      "PassTypeAppleRelevantDate": {
        "type": "object",
        "properties": {
          "endDate": {
            "type": [
              "null",
              "string"
            ],
            "description": "Template-evaluated ISO-8601 date string for the end of the relevancy interval. Optional."
          },
          "startDate": {
            "type": [
              "null",
              "string"
            ],
            "description": "Template-evaluated ISO-8601 date string for the start of the relevancy interval."
          }
        },
        "additionalProperties": false,
        "description": "Configuration for a relevantDates entry. Use `StartDate` alone (no `EndDate`) to let\nWallet auto-calculate the interval, or supply both to define an explicit interval."
      },
      "PassTypeAppleSeat": {
        "type": "object",
        "properties": {
          "seatAisle": {
            "type": [
              "null",
              "string"
            ],
            "description": "The aisle that contains the seat."
          },
          "seatDescription": {
            "type": [
              "null",
              "string"
            ],
            "description": "A description of the seat, such as 'A flat bed seat'."
          },
          "seatIdentifier": {
            "type": [
              "null",
              "string"
            ],
            "description": "The identifier code for the seat."
          },
          "seatLevel": {
            "type": [
              "null",
              "string"
            ],
            "description": "The level that contains the seat."
          },
          "seatNumber": {
            "type": [
              "null",
              "string"
            ],
            "description": "The number of the seat."
          },
          "seatRow": {
            "type": [
              "null",
              "string"
            ],
            "description": "The row that contains the seat."
          },
          "seatSection": {
            "type": [
              "null",
              "string"
            ],
            "description": "The section that contains the seat."
          },
          "seatSectionColor": {
            "type": [
              "null",
              "string"
            ],
            "description": "A color associated with identifying the seat, specified as a CSS-style RGB triple, such as rgb(23,\n187, 82)."
          },
          "seatType": {
            "type": [
              "null",
              "string"
            ],
            "description": "The type of seat, such as 'Reserved seating'."
          }
        },
        "additionalProperties": false,
        "description": "An object that represents the identification of a seat for a transit journey or an event. Source:\nSemanticTagType.Seat.\nhttps://developer.apple.com/documentation/walletpasses/semantictagtype/seat-data.dictionary"
      },
      "PassTypeAppleSemantics": {
        "type": "object",
        "properties": {
          "additionalTicketAttributes": {
            "type": [
              "null",
              "string"
            ],
            "description": "Additional ticket attributes that other tags or keys in the pass don't include. Use this key for any\ntype of event ticket."
          },
          "admissionLevel": {
            "type": [
              "null",
              "string"
            ],
            "description": "The level of admission the ticket provides, such as general admission, VIP, and so forth. Use this\nkey for any type of event ticket."
          },
          "admissionLevelAbbreviation": {
            "type": [
              "null",
              "string"
            ],
            "description": "An abbreviation of the level of admission the ticket provides, such as GA or VIP. Use this key for\nany type of event ticket."
          },
          "albumIDs": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "An array of the Apple Music persistent ID for each album corresponding to the event, in decreasing\norder of significance. Use this key for any type of event ticket."
          },
          "artistIDs": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "An array of the Apple Music persistent ID for each artist performing at the event, in decreasing\norder of significance. Use this key for any type of event ticket."
          },
          "attendeeName": {
            "type": [
              "null",
              "string"
            ],
            "description": "The name of the person the ticket grants admission to. Use this key for any type of event ticket."
          },
          "awayTeamAbbreviation": {
            "type": [
              "null",
              "string"
            ],
            "description": "The unique abbreviation of the away team's name. Use this key only for a sports event ticket."
          },
          "awayTeamLocation": {
            "type": [
              "null",
              "string"
            ],
            "description": "The home location of the away team. Use this key only for a sports event ticket."
          },
          "awayTeamName": {
            "type": [
              "null",
              "string"
            ],
            "description": "The name of the away team. Use this key only for a sports event ticket."
          },
          "balance": {
            "description": "The current balance redeemable with the pass. Use this key only for a store card pass.",
            "$ref": "#/components/schemas/PassTypeAppleCurrencyAmount"
          },
          "duration": {
            "type": [
              "null",
              "string"
            ],
            "description": "The duration of the event or transit journey, in seconds. Use this key for any type of boarding pass\nand any type of event ticket. Sent as a string: whole seconds or a Liquid template."
          },
          "entranceDescription": {
            "type": [
              "null",
              "string"
            ],
            "description": "The long description of the entrance information. Use this key for any type of event ticket."
          },
          "eventEndDate": {
            "type": [
              "null",
              "string"
            ],
            "description": "The date and time the event ends. ISO 8601 date as string. Use this key for any type of event\nticket."
          },
          "eventName": {
            "description": "The full name of the event, such as the title of a movie. Use this key for any type of event ticket.\nShown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "eventStartDate": {
            "type": [
              "null",
              "string"
            ],
            "description": "The date and time the event starts. ISO 8601 date as string. Use this key for any type of event\nticket."
          },
          "eventStartDateInfo": {
            "description": "An object that provides information for the date and time the event starts. Use this key for any\ntype of event ticket. See SemanticTagType.EventDateInfo (iOS 18.0+).",
            "$ref": "#/components/schemas/PassTypeAppleEventDateInfoValue"
          },
          "eventType": {
            "type": [
              "null",
              "string"
            ],
            "description": "The type of event. Use this key for any type of event ticket. Possible values: PKEventTypeGeneric,\nPKEventTypeLivePerformance, PKEventTypeMovie, PKEventTypeSports, PKEventTypeConference,\nPKEventTypeConvention, PKEventTypeWorkshop, PKEventTypeSocialGathering. One of: PKEventTypeGeneric,\nPKEventTypeLivePerformance, PKEventTypeMovie, PKEventTypeSports, PKEventTypeConference,\nPKEventTypeConvention, PKEventTypeWorkshop, PKEventTypeSocialGathering."
          },
          "genre": {
            "type": [
              "null",
              "string"
            ],
            "description": "The genre of the performance, such as classical. Use this key for any type of event ticket."
          },
          "homeTeamAbbreviation": {
            "type": [
              "null",
              "string"
            ],
            "description": "The unique abbreviation of the home team's name. Use this key only for a sports event ticket."
          },
          "homeTeamLocation": {
            "type": [
              "null",
              "string"
            ],
            "description": "The home location of the home team. Use this key only for a sports event ticket."
          },
          "homeTeamName": {
            "type": [
              "null",
              "string"
            ],
            "description": "The name of the home team. Use this key only for a sports event ticket."
          },
          "leagueAbbreviation": {
            "type": [
              "null",
              "string"
            ],
            "description": "The abbreviated league name for a sports event. Use this key only for a sports event ticket."
          },
          "leagueName": {
            "type": [
              "null",
              "string"
            ],
            "description": "The unabbreviated league name for a sports event. Use this key only for a sports event ticket."
          },
          "performerNames": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "An array of the full names of the performers and opening acts at the event, in decreasing order of\nsignificance. Use this key for any type of event ticket."
          },
          "playlistIDs": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "An array of the Apple Music persistent ID for each playlist corresponding to the event, in\ndecreasing order of significance. Use this key for any type of event ticket."
          },
          "seats": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "An object that represents the identification of a seat for a transit journey or an event. Source:\nSemanticTagType.Seat.\nhttps://developer.apple.com/documentation/walletpasses/semantictagtype/seat-data.dictionary",
              "$ref": "#/components/schemas/PassTypeAppleSeat"
            },
            "description": "An array of objects that represent the details for each seat at an event or on a transit journey.\nUse this key for any type of boarding pass or event ticket. See SemanticTagType.Seat."
          },
          "silenceRequested": {
            "type": [
              "null",
              "string"
            ],
            "description": "A Boolean value that determines whether the person's device remains silent during an event or\ntransit journey. The system may override the key and determine the length of the period of silence.\nUse this key for any type of boarding pass or event ticket. Sent as a string: `true`,\n`false` or a Liquid template."
          },
          "sportName": {
            "type": [
              "null",
              "string"
            ],
            "description": "The commonly used name of the sport. Use this key only for a sports event ticket."
          },
          "tailgatingAllowed": {
            "type": [
              "null",
              "string"
            ],
            "description": "A Boolean value that indicates whether tailgating is allowed at the event. Use this key for any type\nof event ticket. Sent as a string: `true`, `false` or a Liquid template."
          },
          "totalPrice": {
            "description": "The total price for the pass. Use this key for any pass type.",
            "$ref": "#/components/schemas/PassTypeAppleCurrencyAmount"
          },
          "venueBoxOfficeOpenDate": {
            "type": [
              "null",
              "string"
            ],
            "description": "The date when the box office opens (ISO 8601). Use this key for any type of event ticket."
          },
          "venueCloseDate": {
            "type": [
              "null",
              "string"
            ],
            "description": "The date when the venue closes (ISO 8601). Use this key for any type of event ticket."
          },
          "venueDoorsOpenDate": {
            "type": [
              "null",
              "string"
            ],
            "description": "The date the doors to the venue open (ISO 8601). Use this key for any type of event ticket."
          },
          "venueEntrance": {
            "type": [
              "null",
              "string"
            ],
            "description": "The full name of the entrance, such as Gate A, to use to gain access to the ticketed event. Use this\nkey for any type of event ticket."
          },
          "venueEntranceDoor": {
            "type": [
              "null",
              "string"
            ],
            "description": "The venue entrance door. Use this key for any type of event ticket."
          },
          "venueEntranceGate": {
            "type": [
              "null",
              "string"
            ],
            "description": "The venue entrance gate. Use this key for any type of event ticket."
          },
          "venueEntrancePortal": {
            "type": [
              "null",
              "string"
            ],
            "description": "The venue entrance portal. Use this key for any type of event ticket."
          },
          "venueFanZoneOpenDate": {
            "type": [
              "null",
              "string"
            ],
            "description": "The date the fan zone opens (ISO 8601). Use this key for any type of event ticket."
          },
          "venueGatesOpenDate": {
            "type": [
              "null",
              "string"
            ],
            "description": "The date the gates to the venue open (ISO 8601). Use this key for any type of event ticket."
          },
          "venueLocation": {
            "description": "An object that represents the geographic coordinates of the venue. Use this key for any type of\nevent ticket. See SemanticTagType.Location.",
            "$ref": "#/components/schemas/PassTypeLocation"
          },
          "venueName": {
            "type": [
              "null",
              "string"
            ],
            "description": "The full name of the venue. Use this key for any type of event ticket."
          },
          "venueOpenDate": {
            "type": [
              "null",
              "string"
            ],
            "description": "The date when the venue opens (ISO 8601). Use this if none of the more specific venue open tags\napply. Use this key for any type of event ticket."
          },
          "venueParkingLotsOpenDate": {
            "type": [
              "null",
              "string"
            ],
            "description": "The date the parking lots open (ISO 8601). Use this key for any type of event ticket."
          },
          "venuePhoneNumber": {
            "type": [
              "null",
              "string"
            ],
            "description": "The phone number for inquiries about the venue's ticketed event. Use this key for any type of event\nticket."
          },
          "venueRegionName": {
            "type": [
              "null",
              "string"
            ],
            "description": "The name of the city or hosting region of the venue. Use this key for any type of event ticket."
          },
          "venueRoom": {
            "type": [
              "null",
              "string"
            ],
            "description": "The full name of the room where the ticketed event is to take place. Use this key for any type of\nevent ticket."
          },
          "wifiAccess": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "An object that contains information required to connect to a Wi-Fi network. See\nSemanticTagType.WifiNetwork.",
              "$ref": "#/components/schemas/PassTypeAppleWifiNetwork"
            },
            "description": "An array of objects that represent the Wi-Fi networks associated with the event; for example, the\nnetwork name and password associated with a developer conference. Use this key for any type of pass.\nSee SemanticTagType.WifiNetwork."
          }
        },
        "additionalProperties": false,
        "description": "Apple Wallet semantic tags of the pass, as documented in Apple's SemanticTags specification."
      },
      "PassTypeAppleStampImage": {
        "type": "object",
        "properties": {
          "artWork": {
            "type": [
              "null",
              "string"
            ],
            "description": "Poster artwork, used only when the template enables the poster layout."
          },
          "count": {
            "type": [
              "null",
              "integer"
            ],
            "description": "The stamp count these images are shown at.",
            "format": "int32"
          },
          "strip": {
            "type": [
              "null",
              "string"
            ],
            "description": "Strip image for the classic store-card layout."
          }
        },
        "additionalProperties": false,
        "description": "The Apple images a stamp card shows at one exact stamp count."
      },
      "PassTypeAppleUpcomingPassInformation": {
        "type": "object",
        "properties": {
          "actionLinks": {
            "description": "A collection of URLs used to populate UI elements in the details view.",
            "$ref": "#/components/schemas/PassTypeAppleActionLinks"
          },
          "additionalInfoFields": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Information about a field.",
              "$ref": "#/components/schemas/PassTypeAppleField"
            },
            "description": "The fields of information displayed on the Additional Info section below a pass."
          },
          "backFields": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Information about a field.",
              "$ref": "#/components/schemas/PassTypeAppleField"
            },
            "description": "The fields of information displayed on the details view of the upcoming pass information entry."
          },
          "dateInformation": {
            "description": "Information about the start and end time of the upcoming pass information entry. If omitted, the\nentry is labeled as TBD.",
            "$ref": "#/components/schemas/PassTypeAppleDateInformation"
          },
          "identifier": {
            "type": [
              "null",
              "string"
            ],
            "description": "(Required) A string that uniquely identifies the upcoming pass information entry. The identifier\nneeds to be unique for each upcoming information entry."
          },
          "images": {
            "description": "A collection of image names used to populate images in the details view.",
            "$ref": "#/components/schemas/PassTypeAppleImages"
          },
          "isActive": {
            "type": [
              "null",
              "string"
            ],
            "description": "Indicates whether the upcoming pass information entry is currently active. The default value is\nfalse."
          },
          "name": {
            "type": [
              "null",
              "string"
            ],
            "description": "(Required) The name of the upcoming pass information entry. A Liquid template, not a translatable\nstring: one value for every language."
          },
          "semantics": {
            "description": "The semantic, machine-readable metadata about the upcoming pass information entry.",
            "$ref": "#/components/schemas/PassTypeAppleSemantics"
          },
          "type": {
            "type": [
              "null",
              "string"
            ],
            "description": "(Required) The type of upcoming pass information entry. Value: event."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Apple configuration."
      },
      "PassTypeAppleWifiNetwork": {
        "type": "object",
        "properties": {
          "password": {
            "type": [
              "null",
              "string"
            ],
            "description": "Wi-Fi password (if any)."
          },
          "ssid": {
            "type": [
              "null",
              "string"
            ],
            "description": "Wi-Fi SSID (network name)."
          }
        },
        "additionalProperties": false,
        "description": "An object that contains information required to connect to a Wi-Fi network. See\nSemanticTagType.WifiNetwork."
      },
      "PassTypeDetail": {
        "required": [
          "configuration",
          "languages",
          "name"
        ],
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "Name of the template, unique within the tenant."
          },
          "configuration": {
            "description": "The template itself, with every translatable value carrying its wording.",
            "$ref": "#/components/schemas/PassTypeModel"
          },
          "languages": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Languages this template has wording in, as language codes."
          }
        },
        "additionalProperties": false,
        "description": "One pass template in full."
      },
      "PassTypeExtensions": {
        "type": "object",
        "properties": {
          "apple": {
            "description": "The Apple Wallet pass. Configured the same way whatever the kind.",
            "$ref": "#/components/schemas/PassTypeApple"
          },
          "google": {
            "description": "The Google Wallet card. Each kind accepts only the properties it declares — every property that is\nnot common to all six says which kinds it applies to.",
            "$ref": "#/components/schemas/PassTypeGoogle"
          },
          "preview": {
            "description": "How an issued pass of this template is summarised in the back office.",
            "$ref": "#/components/schemas/PassTypePreview"
          },
          "scannableData": {
            "description": "What a scanner reads off an issued pass.",
            "$ref": "#/components/schemas/PassTypeScannableData"
          },
          "stamps": {
            "description": "The stamp mechanic. Only a Neo.Web.Api.Wallet.Controllers.PassTypes.PassTypeKind.StampCard has one.",
            "$ref": "#/components/schemas/PassTypeStamps"
          },
          "metadata": {
            "description": "Values computed whenever a pass is updated, which issued passes can then be searched and filtered\nby. Nothing here is shown to the holder.",
            "$ref": "#/components/schemas/PassTypeMetadata"
          }
        },
        "additionalProperties": false,
        "description": "The two wallets and the sections that configure neither of them on its own."
      },
      "PassTypeGoogle": {
        "type": "object",
        "properties": {
          "accountId": {
            "type": [
              "null",
              "string"
            ],
            "description": "The loyalty account identifier. Recommended maximum length is 20 characters. Applies to:\ncustomerCard, stampCard."
          },
          "accountIdLabel": {
            "description": "The account ID label, such as \"Member ID.\" Recommended maximum length is 15 characters to ensure\nfull string is displayed on smaller screens. Applies to: customerCard, stampCard. Shown to the pass\nholder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "accountName": {
            "type": [
              "null",
              "string"
            ],
            "description": "The loyalty account holder name, such as \"John Smith.\" Recommended maximum length is 20 characters\nto ensure full string is displayed on smaller screens. Applies to: customerCard, stampCard."
          },
          "accountNameLabel": {
            "description": "The account name label, such as \"Member Name.\" Recommended maximum length is 15 characters to ensure\nfull string is displayed on smaller screens. Applies to: customerCard, stampCard. Shown to the pass\nholder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "additionalLinks": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Part of the Google configuration.",
              "$ref": "#/components/schemas/PassTypeGoogleUri"
            },
            "description": "Links module data."
          },
          "allowBarCodeRedemption": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Determines whether the merchant supports gift card redemption using barcode. If `true`, app\ndisplays a barcode for the gift card on the Gift card details screen. If false, a `barcode` is\nnot displayed. Applies to: giftCard."
          },
          "appLinks": {
            "description": "Optional information about the partner app link.",
            "$ref": "#/components/schemas/PassTypeGoogleAppLinkInfos"
          },
          "balance": {
            "description": "The card's monetary balance. Applies to: giftCard.",
            "$ref": "#/components/schemas/PassTypeGoogleMoney"
          },
          "balanceUpdateTime": {
            "type": [
              "null",
              "string"
            ],
            "description": "The date and time when the balance was last updated. If balance is updated and this property is not\nprovided, system will default to the current time. Applies to: giftCard."
          },
          "barCode": {
            "description": "The barcode type and value.",
            "$ref": "#/components/schemas/PassTypeGoogleBarCode"
          },
          "cardNumber": {
            "type": [
              "null",
              "string"
            ],
            "description": "The card's number. Applies to: giftCard."
          },
          "cardNumberLabel": {
            "type": [
              "null",
              "string"
            ],
            "description": "Translated strings for the card_number_label. Applies to: giftCard."
          },
          "confirmationCode": {
            "type": [
              "null",
              "string"
            ],
            "description": "The confirmation code of the event reservation. This may also take the form of an \"order number\",\n\"confirmation number\", \"reservation number\", or other equivalent. Applies to: eventTicket."
          },
          "confirmationCodeLabel": {
            "type": [
              "null",
              "string"
            ],
            "description": "The label to use for the confirmation code value\n(eventTicketObject.reservationInfo.confirmationCode) on the card detail view. Each available option\nmaps to a set of localized strings, so that translations are shown to the user based on their\nlocale. Both confirmationCodeLabel and customConfirmationCodeLabel may not be set. If neither is\nset, the label will default to \"Confirmation Code\", localized. If the confirmation code field is\nunset, this label will not be used. Applies to: eventTicket. One of:\nCONFIRMATION_CODE_LABEL_UNSPECIFIED, CONFIRMATION_CODE, CONFIRMATION_NUMBER, ORDER_NUMBER,\nRESERVATION_NUMBER."
          },
          "countryCode": {
            "type": [
              "null",
              "string"
            ],
            "description": "ISO 3166-1 alpha-2 country code used to display and localize the pass. Applies to: customerCard,\neventTicket, giftCard, offer, stampCard."
          },
          "customConfirmationLabel": {
            "description": "A custom label to use for the confirmation code value\n(eventTicketObject.reservationInfo.confirmationCode) on the card detail view. This should only be\nused if the default \"Confirmation Code\" label or one of the confirmationCodeLabel options is not\nsufficient. Both confirmationCodeLabel and customConfirmationCodeLabel may not be set. If neither is\nset, the label will default to \"Confirmation Code\", localized. If the confirmation code field is\nunset, this label will not be used. Applies to: eventTicket. Shown to the pass holder, so it carries\none value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "dateTimeDetails": {
            "description": "Date time details of the pass. Applies to: eventTicket.",
            "$ref": "#/components/schemas/PassTypeGoogleDateTimeDetails"
          },
          "details": {
            "description": "The details of the offer. This property is localizable. Applies to: offer. Shown to the pass holder,\nso it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "disableExpirationNotification": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Indicates whether Google Wallet should suppress expiration notifications for the offer. Applies to:\noffer."
          },
          "discoverableProgram": {
            "description": "Information about how the class may be discovered and instantiated from within the Google Wallet\napp. Applies to: customerCard, stampCard.",
            "$ref": "#/components/schemas/PassTypeGoogleDiscoverableProgram"
          },
          "eventId": {
            "type": [
              "null",
              "string"
            ],
            "description": "The ID of the event. This ID should be unique for every event in an account. It is used to group\ntickets together if the user has saved multiple tickets for the same event. It can be at most 64\ncharacters. If provided, the grouping will be stable.Be wary of unintentional collision to avoid\ngrouping tickets that should not be grouped.If you use only one class per event, you can simply set\nthis to the classId(with or without the issuer ID portion). If not provided, the platform will\nattempt to use other data to group tickets(potentially unstable). Applies to: eventTicket."
          },
          "eventName": {
            "description": "The name of the event, such as \"LA Dodgers at SF Giants\". This string is localizable. Applies to:\neventTicket. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "eventNumber": {
            "type": [
              "null",
              "string"
            ],
            "description": "The card's event number, an optional field used by some gift cards. Applies to: giftCard."
          },
          "eventNumberLabel": {
            "description": "The label to display for event number, such as \"Target Event #\". This property is localizable.\nApplies to: giftCard. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "expiryNotification": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Indicates that the issuer would like GooglePay to send expiry notifications 2 days prior to the card\nexpiration. Applies to: generic."
          },
          "faceValue": {
            "description": "The face value of the ticket, matching what would be printed on a physical version of the ticket.\nApplies to: eventTicket.",
            "$ref": "#/components/schemas/PassTypeGoogleMoney"
          },
          "finePrint": {
            "description": "The fine print or terms of the pass, such as \"20% off any t-shirt at Adam's Apparel.\" This property\nis localizable. Applies to: eventTicket, offer. Shown to the pass holder, so it carries one value\nper language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "gate": {
            "description": "Gate seat information. Applies to: eventTicket.",
            "$ref": "#/components/schemas/PassTypeGoogleGate"
          },
          "header": {
            "description": "Required. The title of the pass, such as \"50% off coupon\" or \"Library card\" or \"Voucher\". This field\nis required and appears in the title row of the pass detail view. Applies to: generic. Shown to the\npass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "helpUrl": {
            "description": "The help link for the offer, such as http://myownpersonaldomain.com/help. Applies to: offer.",
            "$ref": "#/components/schemas/PassTypeGoogleUri"
          },
          "heroImage": {
            "type": [
              "null",
              "string"
            ],
            "description": "Optional banner image displayed on the front of the card. If none is present, nothing will be\ndisplayed. The image will display at 100% width."
          },
          "hexBackgroundColor": {
            "type": [
              "null",
              "string"
            ],
            "description": "The background color for the card. If not set the dominant color of the hero image is used, and if\nno hero image is set, the dominant color of the logo is used. The format is #rrggbb where rrggbb is\na hex RGB triplet, such as #ffcc00. You can also use the shorthand version of the RGB triplet which\nis #rgb, such as #fc0."
          },
          "homepage": {
            "description": "The URI of your application's home page. Populating the URI in this field results in the exact same\nbehavior as populating an URI in linksModuleData (when an object is rendered, a link to the homepage\nis shown in what would usually be thought of as the linksModuleData section of the object). Applies\nto: customerCard, eventTicket, giftCard, offer, stampCard.",
            "$ref": "#/components/schemas/PassTypeGoogleUri"
          },
          "identifier": {
            "type": [
              "null",
              "string"
            ],
            "description": "Name of the Google class. If `null` `{tenantId}.{passType}` will be used. It's an advanced\nconfiguration and should be keep null except if google class is already created. It could be the\ncase if pass are imported from another system."
          },
          "issuerName": {
            "description": "The issuer name. Recommended maximum length is 20 characters to ensure full string is displayed on\nsmaller screens. Applies to: customerCard, eventTicket, giftCard, offer, stampCard. Shown to the\npass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "locations": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "An object that represents the coordinates of a location. See SemanticTagType.Location.",
              "$ref": "#/components/schemas/PassTypeLocation"
            },
            "description": "The list of locations where the object can be used. The platform uses this information to trigger\ngeolocated notifications to users."
          },
          "logo": {
            "type": [
              "null",
              "string"
            ],
            "description": "The logo image of the pass. This image is displayed in the card detail view in upper left, and also\non the list/thumbnail view. If the logo is not present, the first letter of cardTitle would be shown\nas logo. Applies to: eventTicket, generic."
          },
          "loyaltyPoints": {
            "description": "The loyalty reward points label, balance, and type. Applies to: customerCard, stampCard.",
            "$ref": "#/components/schemas/PassTypeGoogleLoyaltyPoint"
          },
          "merchantName": {
            "description": "Merchant name, such as \"Adam's Apparel\". The app may display an ellipsis after the first 20\ncharacters to ensure full string is displayed on smaller screens. This property is localizable.\nApplies to: giftCard. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "messages": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Part of the Google configuration.",
              "$ref": "#/components/schemas/PassTypeGoogleMessage"
            },
            "description": "An array of messages displayed in the app. All users of this object will receive its associated\nmessages. The maximum number of these fields is 10."
          },
          "multipleDevicesAndHoldersAllowedStatus": {
            "type": [
              "null",
              "string"
            ],
            "description": "Identifies whether multiple users and devices will save the same object referencing this class. One\nof: MultipleHolder, OneUserAllDevices, OneUserOneDevice."
          },
          "screenshotEligibility": {
            "type": [
              "null",
              "string"
            ],
            "description": "Whether the holder can take a screenshot of the pass in Google Wallet on Android. One of: Unspecified,\nEligible, Ineligible."
          },
          "nfcConstraints": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "What the phone must not hand out over NFC while the pass is open. Each one of: BlockPayment,\nBlockClosedLoopTransit."
          },
          "grouping": {
            "description": "How passes are grouped together in Google Wallet.",
            "$ref": "#/components/schemas/PassTypeGoogleGrouping"
          },
          "imageModule": {
            "description": "An image shown at full width among the details of the pass.",
            "$ref": "#/components/schemas/PassTypeGoogleImageModule"
          },
          "pin": {
            "type": [
              "null",
              "string"
            ],
            "description": "The card's PIN. Applies to: giftCard."
          },
          "pinLabel": {
            "description": "The label to display for the PIN, such as \"4-digit PIN\". This property is localizable. Applies to:\ngiftCard. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "programLogo": {
            "type": [
              "null",
              "string"
            ],
            "description": "Required. The logo of the loyalty program or company. This logo is displayed in both the details and\nlist views of the app. Applies to: customerCard, giftCard, stampCard."
          },
          "programName": {
            "description": "The program name, such as \"Adam's Apparel\". The app may display an ellipsis after the first 20\ncharacters to ensure full string is displayed on smaller screens. Applies to: customerCard,\nstampCard. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "provider": {
            "description": "The offer provider (either the aggregator name or merchant name). Recommended maximum length is 12\ncharacters to ensure full string is displayed on smaller screens. This property is localizable.\nApplies to: offer. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "redemptionChannel": {
            "type": [
              "null",
              "string"
            ],
            "description": "The redemption channels applicable to this offer. Applies to: offer. One of:\nREDEMPTION_CHANNEL_UNSPECIFIED, INSTORE, ONLINE, BOTH, TEMPORARY_PRICE_REDUCTION."
          },
          "rewardsTier": {
            "type": [
              "null",
              "string"
            ],
            "description": "The rewards tier, such as \"Gold\" or \"Platinum.\" Recommended maximum length is 7 characters to ensure\nfull string is displayed on smaller screens. Applies to: customerCard, stampCard."
          },
          "rewardsTierLabel": {
            "description": "The rewards tier label, such as \"Rewards Tier.\" Recommended maximum length is 9 characters to ensure\nfull string is displayed on smaller screens. Applies to: customerCard, stampCard. Shown to the pass\nholder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "row": {
            "description": "Row seat information. Applies to: eventTicket.",
            "$ref": "#/components/schemas/PassTypeGoogleRow"
          },
          "seat": {
            "description": "Seat information. Applies to: eventTicket.",
            "$ref": "#/components/schemas/PassTypeGoogleSeat"
          },
          "secondaryLoyaltyPoints": {
            "description": "The secondary loyalty reward points label, balance, and type. Shown in addition to the primary\nloyalty points. Applies to: customerCard, stampCard.",
            "$ref": "#/components/schemas/PassTypeGoogleLoyaltyPoint"
          },
          "secondaryRewardsTier": {
            "type": [
              "null",
              "string"
            ],
            "description": "The secondary rewards tier, such as \"Gold\" or \"Platinum.\". Applies to: customerCard, stampCard."
          },
          "secondaryRewardsTierLabel": {
            "description": "The secondary rewards tier label, such as \"Rewards Tier.\". Applies to: customerCard, stampCard.\nShown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "section": {
            "description": "Section seat information. Applies to: eventTicket.",
            "$ref": "#/components/schemas/PassTypeGoogleSection"
          },
          "securityAnimation": {
            "type": [
              "null",
              "string"
            ],
            "description": "Optional information about the security animation. If this is set a security animation will be\nrendered on pass details. One of: Unspecified, FoilShimmer."
          },
          "shortTitle": {
            "description": "A shortened version of the title of the offer, such as \"20% off,\" shown to users as a quick\nreference to the offer contents. Recommended maximum length is 20 characters. This property is\nlocalizable. Applies to: offer. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "smartTap": {
            "description": "Identifies whether this class supports Smart Tap.",
            "$ref": "#/components/schemas/PassTypeGoogleSmartTap"
          },
          "stampImages": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "The Google image a stamp card shows at one exact stamp count.",
              "$ref": "#/components/schemas/PassTypeGoogleStampImage"
            },
            "description": "The hero image to show at each stamp count. The entry matching the holder's current count replaces\nthe class-level hero image. Applies to: stampCard."
          },
          "state": {
            "type": [
              "null",
              "string"
            ],
            "description": "The state of the object. This field is used to determine how an object is displayed in the app. For\nexample, an inactive object is moved to the \"Expired passes\" section. Available Values are ACTIVE,\nCOMPLETED, EXPIRED, INACTIVE."
          },
          "subheader": {
            "description": "The title label of the pass, such as location where this pass can be used. Appears right above the\ntitle in the title row in the pass detail view. Applies to: generic. Shown to the pass holder, so it\ncarries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "templateOverride": {
            "description": "Which values the card shows where, in place of Google's default layout.",
            "$ref": "#/components/schemas/PassTypeGoogleTemplateOverride"
          },
          "texts": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Part of the Google configuration.",
              "$ref": "#/components/schemas/PassTypeGoogleText"
            },
            "description": "Text module data."
          },
          "ticketHolderName": {
            "type": [
              "null",
              "string"
            ],
            "description": "Name of the ticket holder, if the ticket is assigned to a person. E.g. \"John Doe\" or \"Jane Doe\".\nApplies to: eventTicket."
          },
          "ticketNumber": {
            "type": [
              "null",
              "string"
            ],
            "description": "The number of the ticket. This can be a unique identifier across all tickets in an issuer's system,\nall tickets for the event (e.g. XYZ1234512345), or all tickets in the order (1, 2, 3, etc.). Applies\nto: eventTicket."
          },
          "ticketType": {
            "description": "The type of the ticket, such as \"Adult\" or \"Child\", or \"VIP\" or \"Standard\". This property is\nlocalizable. Applies to: eventTicket. Shown to the pass holder, so it carries one value per\nlanguage.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "title": {
            "description": "The title of the offer, such as \"20% off any t-shirt.\" Recommended maximum length is 60 characters\nto ensure full string is displayed on smaller screens. This property is localizable. Applies to:\ngeneric, offer. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "titleImage": {
            "type": [
              "null",
              "string"
            ],
            "description": "The title image of the offer. This image is displayed in both the details and list views of the app.\nApplies to: offer."
          },
          "upcomingNotification": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Indicates that the issuer would like GooglePay send an upcoming card validity notification 1 day\nbefore card becomes valid/usable. Applies to: generic."
          },
          "validTimeInterval": {
            "description": "The time period this object will be active and object can be used. An object's state will be changed\nto expired when this time period has passed.",
            "$ref": "#/components/schemas/PassTypeGoogleTimeInterval"
          },
          "valueAddedOpportunities": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "Part of the Google configuration.",
              "$ref": "#/components/schemas/PassTypeGoogleValueAddedItem"
            },
            "description": "Optional value added module data. Maximum of ten on the object."
          },
          "venue": {
            "description": "Event venue details. Applies to: eventTicket.",
            "$ref": "#/components/schemas/PassTypeGoogleVenue"
          },
          "viewUnlockRequirement": {
            "type": [
              "null",
              "string"
            ],
            "description": "View Unlock Requirement. One of: Unspecified, RequiredToView, NotRequired."
          },
          "wideLogo": {
            "type": [
              "null",
              "string"
            ],
            "description": "he wide logo of the pass. When provided, this will be used in place of the logo in the top left of\nthe card view. Applies to: eventTicket, generic."
          },
          "wideProgramLogo": {
            "type": [
              "null",
              "string"
            ],
            "description": "The wide logo of the loyalty program or company. When provided, this will be used in place of the\nprogram logo in the top left of the card view. Applies to: customerCard, giftCard, stampCard."
          },
          "wideTitleImage": {
            "type": [
              "null",
              "string"
            ],
            "description": "The wide title image used in place of the title image in the top left of the card view. Applies to:\noffer."
          }
        },
        "additionalProperties": false,
        "description": "The Google Wallet card. Not every pass kind accepts every property, and one that only some kinds\naccept says so."
      },
      "PassTypeGoogleAndroidAppLinkInfo": {
        "type": "object",
        "properties": {
          "packageName": {
            "type": [
              "null",
              "string"
            ],
            "description": "Package name for AppTarget. For example: com.google.android.gm."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleAppLinkInfos": {
        "type": "object",
        "properties": {
          "androidAppLinkInfo": {
            "description": "Optional information about the partner app link. If included, the app link link module will be\nrendered on the valuable details on the android client.",
            "$ref": "#/components/schemas/PassTypeGoogleAndroidAppLinkInfo"
          },
          "displayText": {
            "description": "Optional display text for the app link button. Character limit is 30. Shown to the pass holder, so\nit carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "webAppLinkInfo": {
            "description": "Optional information about the partner app link. If included, the app link link module will be\nrendered on the valuable details on the web client.",
            "$ref": "#/components/schemas/PassTypeGoogleWebAppLinkInfo"
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleBalanceConfigurationBase": {
        "type": "object",
        "properties": {
          "value": {
            "type": [
              "null",
              "string"
            ],
            "description": "Value of the pass. A Liquid template, not a translatable string: one value for every language."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleBarCode": {
        "type": "object",
        "properties": {
          "alternateText": {
            "type": [
              "null",
              "string"
            ],
            "description": "A human readable equivalent of the barcode value, shown under the barcode in place of the default\ntext. Not allowed on a TEXT_ONLY barcode."
          },
          "showCodeText": {
            "description": "Text shown when a Smart Tap barcode is hidden behind a click action. Shown to the pass holder, so\nit carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "type": {
            "type": [
              "null",
              "string"
            ],
            "description": "The type of barcode. Only QR_CODE is supported for rotating barcodes. One of: AZTEC, CODE_39,\nCODE_128, CODABAR, DATA_MATRIX, EAN_8, EAN_13, ITF_14, PDF_417, QR_CODE, UPC_A, TEXT_ONLY."
          },
          "value": {
            "type": [
              "null",
              "string"
            ],
            "description": "The value encoded in the barcode."
          },
          "rotating": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "The phone recomputes the code every period from a one-time password (QR_CODE and PDF_417 only). The value must\nhold {totp_value_0}, replaced by the current password."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleBarcodeInfo": {
        "type": "object",
        "properties": {
          "firstBottomDetail": {
            "description": "Value shown below the barcode.",
            "$ref": "#/components/schemas/PassTypeGoogleDetail"
          },
          "firstTopDetail": {
            "description": "First value shown above the barcode.",
            "$ref": "#/components/schemas/PassTypeGoogleDetail"
          },
          "secondTopDetail": {
            "description": "Second value shown above the barcode.",
            "$ref": "#/components/schemas/PassTypeGoogleDetail"
          }
        },
        "additionalProperties": false,
        "description": "The values shown around the barcode of the card."
      },
      "PassTypeGoogleCardTemplateInfo": {
        "type": "object",
        "properties": {
          "firstLine": {
            "description": "First row. Required once the card layout is overridden.",
            "$ref": "#/components/schemas/PassTypeGoogleCardTemplateInfoRow"
          },
          "lines": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "One row on the front of the card: one to three slots, left to right.",
              "$ref": "#/components/schemas/PassTypeGoogleCardTemplateInfoRow"
            },
            "description": "The configured rows in display order. Read-only: derived from `firstLine`, `secondLine`\nand `thirdLine`, and ignored on save."
          },
          "secondLine": {
            "description": "Second row.",
            "$ref": "#/components/schemas/PassTypeGoogleCardTemplateInfoRow"
          },
          "thirdLine": {
            "description": "Third row. Shown only when `secondLine` is set.",
            "$ref": "#/components/schemas/PassTypeGoogleCardTemplateInfoRow"
          }
        },
        "additionalProperties": false,
        "description": "The rows of values on the front of the card, top to bottom."
      },
      "PassTypeGoogleCardTemplateInfoItem": {
        "type": "object",
        "properties": {
          "primary": {
            "description": "Value shown in the slot.",
            "$ref": "#/components/schemas/PassTypeGoogleCardTemplateInfoItemValue"
          },
          "secondary": {
            "description": "Value shown beside the primary one in the same slot, separated by a slash.",
            "$ref": "#/components/schemas/PassTypeGoogleCardTemplateInfoItemValue"
          }
        },
        "additionalProperties": false,
        "description": "One slot of a row on the front of the card."
      },
      "PassTypeGoogleCardTemplateInfoItemValue": {
        "type": "object",
        "properties": {
          "dateFormat": {
            "type": [
              "null",
              "string"
            ],
            "description": "How a date value is rendered. One of: DATE_FORMAT_UNSPECIFIED, DATE_TIME, DATE_ONLY, TIME_ONLY,\nDATE_TIME_YEAR, DATE_YEAR, YEAR_MONTH, YEAR_MONTH_DAY."
          },
          "paths": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Google field paths to read the value from, such as `object.textModulesData['points']`. The first\none holding a value is shown."
          }
        },
        "additionalProperties": false,
        "description": "A value on the front of the card, read from a field of the Google object or class."
      },
      "PassTypeGoogleCardTemplateInfoRow": {
        "type": "object",
        "properties": {
          "firstItem": {
            "description": "First slot. Required.",
            "$ref": "#/components/schemas/PassTypeGoogleCardTemplateInfoItem"
          },
          "items": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "One slot of a row on the front of the card.",
              "$ref": "#/components/schemas/PassTypeGoogleCardTemplateInfoItem"
            },
            "description": "The configured slots in display order. Read-only: derived from `firstItem`, `secondItem`\nand `thirdItem`, and ignored on save."
          },
          "secondItem": {
            "description": "Second slot.",
            "$ref": "#/components/schemas/PassTypeGoogleCardTemplateInfoItem"
          },
          "thirdItem": {
            "description": "Third slot. Shown only when `secondItem` is set.",
            "$ref": "#/components/schemas/PassTypeGoogleCardTemplateInfoItem"
          }
        },
        "additionalProperties": false,
        "description": "One row on the front of the card: one to three slots, left to right."
      },
      "PassTypeGoogleDateTimeDetails": {
        "type": "object",
        "properties": {
          "customDoorsOpenLabel": {
            "description": "A custom label to use for the doors open value (doorsOpen) on the card detail view. This should only\nbe used if the default \"Doors Open\" label or one of the doorsOpenLabel options is not sufficient.\nBoth doorsOpenLabel and customDoorsOpenLabel may not be set.If neither is set, the label will\ndefault to \"Doors Open\", localized.If the doors open field is unset, this label will not be used.\nShown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "doorsOpen": {
            "type": [
              "null",
              "string"
            ],
            "description": "The date/time when the doors open at the venue. This is an ISO 8601 extended format date/time, with\nor without an offset.Time may be specified up to nanosecond precision. Offsets may be specified with\nseconds precision (even though offset seconds is not part of ISO 8601). For example:\n1985-04-12T23:20:50.52Z would be 20 minutes and 50.52 seconds after the 23rd hour of April 12th,\n1985 in UTC. 1985-04-12T19:20:50.52-04:00 would be 20 minutes and 50.52 seconds after the 19th hour\nof April 12th, 1985, 4 hours before UTC(same instant in time as the above example). If the event\nwere in New York, this would be the equivalent of Eastern Daylight Time (EDT). Remember that offset\nvaries in regions that observe Daylight Saving Time(or Summer Time), depending on the time of the\nyear. 1985-04-12T19:20:50.52 would be 20 minutes and 50.52 seconds after the 19th hour of April\n12th, 1985 with no offset information. The portion of the date/time without the offset is considered\nthe \"local date/time\". This should be the local date/time at the venue. For example, if the event\noccurs at the 20th hour of June 5th, 2018 at the venue, the local date/time portion should be\n2018-06-05T20:00:00. If the local date/time at the venue is 4 hours before UTC, an offset of -04:00\nmay be appended. Without offset information, some rich features may not be available."
          },
          "doorsOpenLabel": {
            "type": [
              "null",
              "string"
            ],
            "description": "The label to use for the doors open value (doorsOpen) on the card detail view. Each available option\nmaps to a set of localized strings, so that translations are shown to the user based on their\nlocale. Both doorsOpenLabel and customDoorsOpenLabel may not be set.If neither is set, the label\nwill default to \"Doors Open\", localized.If the doors open field is unset, this label will not be\nused. One of: DOORS_OPEN_LABEL_UNSPECIFIED, DOORS_OPEN, GATES_OPEN."
          },
          "end": {
            "type": [
              "null",
              "string"
            ],
            "description": "The date/time when the event ends. If the event spans multiple days, it should be the end date/time\non the last day. This is an ISO 8601 extended format date/time, with or without an offset.Time may\nbe specified up to nanosecond precision.Offsets may be specified with seconds precision (even though\noffset seconds is not part of ISO 8601). For example: 1985-04-12T23:20:50.52Z would be 20 minutes\nand 50.52 seconds after the 23rd hour of April 12th, 1985 in UTC. 1985-04-12T19:20:50.52-04:00 would\nbe 20 minutes and 50.52 seconds after the 19th hour of April 12th, 1985, 4 hours before UTC(same\ninstant in time as the above example). If the event were in New York, this would be the equivalent\nof Eastern Daylight Time (EDT). Remember that offset varies in regions that observe Daylight Saving\nTime(or Summer Time), depending on the time of the year. 1985-04-12T19:20:50.52 would be 20 minutes\nand 50.52 seconds after the 19th hour of April 12th, 1985 with no offset information. The portion of\nthe date/time without the offset is considered the \"local date/time\". This should be the local\ndate/time at the venue. For example, if the event occurs at the 20th hour of June 5th, 2018 at the\nvenue, the local date/time portion should be 2018-06-05T20:00:00. If the local date/time at the\nvenue is 4 hours before UTC, an offset of -04:00 may be appended. Without offset information, some\nrich features may not be available."
          },
          "start": {
            "type": [
              "null",
              "string"
            ],
            "description": "The date/time when the event starts.If the event spans multiple days, it should be the start\ndate/time on the first day. This is an ISO 8601 extended format date/time, with or without an\noffset.Time may be specified up to nanosecond precision.Offsets may be specified with seconds\nprecision (even though offset seconds is not part of ISO 8601). For example: 1985-04-12T23:20:50.52Z\nwould be 20 minutes and 50.52 seconds after the 23rd hour of April 12th, 1985 in UTC.\n1985-04-12T19:20:50.52-04:00 would be 20 minutes and 50.52 seconds after the 19th hour of April\n12th, 1985, 4 hours before UTC(same instant in time as the above example). If the event were in New\nYork, this would be the equivalent of Eastern Daylight Time (EDT). Remember that offset varies in\nregions that observe Daylight Saving Time(or Summer Time), depending on the time of the year.\n1985-04-12T19:20:50.52 would be 20 minutes and 50.52 seconds after the 19th hour of April 12th, 1985\nwith no offset information. The portion of the date/time without the offset is considered the \"local\ndate/time\". This should be the local date/time at the venue. For example, if the event occurs at the\n20th hour of June 5th, 2018 at the venue, the local date/time portion should be 2018-06-05T20:00:00.\nIf the local date/time at the venue is 4 hours before UTC, an offset of -04:00 may be appended.\nWithout offset information, some rich features may not be available."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleDetail": {
        "type": "object",
        "properties": {
          "paths": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Google field paths to read the value from. The first one holding a value is shown."
          }
        },
        "additionalProperties": false,
        "description": "A value shown next to the barcode, read from a field of the Google object or class."
      },
      "PassTypeGoogleDetailsItem": {
        "type": "object",
        "properties": {
          "firstValuePaths": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Google field paths of the entry's value. The first one holding a value is shown."
          },
          "secondValuePaths": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Google field paths of a second value shown beside the first, separated by a slash."
          }
        },
        "additionalProperties": false,
        "description": "One entry of the card's details view."
      },
      "PassTypeGoogleDetailsTemplateOverride": {
        "type": "object",
        "properties": {
          "items": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "One entry of the card's details view.",
              "$ref": "#/components/schemas/PassTypeGoogleDetailsItem"
            },
            "description": "The entries, in display order."
          }
        },
        "additionalProperties": false,
        "description": "The order and content of the card's details view."
      },
      "PassTypeGoogleDiscoverableProgram": {
        "type": "object",
        "properties": {
          "signinUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "The URL to direct the user to for the merchant's signin site. Used when MERCHANT_HOSTED_SIGNIN is\nenabled."
          },
          "signupSharedDatas": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "User data that is sent in a POST request to the signup website URL. Valid values are Google Wallet\nSharedDataType strings such as FIRST_NAME, LAST_NAME, EMAIL, etc."
          },
          "signupUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "The URL to direct the user to for the merchant's signup site. Used when MERCHANT_HOSTED_SIGNUP is\nenabled."
          },
          "state": {
            "type": [
              "null",
              "string"
            ],
            "description": "Visibility state of the discoverable program. One of: trustedTesters, live, disabled."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleGate": {
        "type": "object",
        "properties": {
          "customGateLabel": {
            "description": "A custom label to use for the gate value (eventTicketObject.seatInfo.gate) on the card detail view.\nThis should only be used if the default \"Gate\" label or one of the gateLabel options is not\nsufficient. Both gateLabel and customGateLabel may not be set. If neither is set, the label will\ndefault to \"Gate\", localized. If the gate field is unset, this label will not be used. This property\nis localizable. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "gate": {
            "type": [
              "null",
              "string"
            ],
            "description": "The gate the ticket holder should enter to get to their seat, such as \"A\" or \"West\". This field is\nlocalizable so you may translate words or use different alphabets for the characters in an\nidentifier."
          },
          "gateLabel": {
            "type": [
              "null",
              "string"
            ],
            "description": "The label to use for the gate value (eventTicketObject.seatInfo.gate) on the card detail view. Each\navailable option maps to a set of localized strings, so that translations are shown to the user\nbased on their locale. Both gateLabel and customGateLabel may not be set. If neither is set, the\nlabel will default to \"Gate\", localized. If the gate field is unset, this label will not be used.\nOne of: GATE_LABEL_UNSPECIFIED, GATE, DOOR, ENTRANCE."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleGrouping": {
        "type": "object",
        "properties": {
          "id": {
            "type": [
              "null",
              "string"
            ],
            "description": "The group the pass belongs to: passes with the same id are shown stacked together."
          },
          "sortIndex": {
            "type": [
              "null",
              "string"
            ],
            "description": "The pass's position in its group, lower first."
          }
        },
        "additionalProperties": false,
        "description": "How passes are grouped together in Google Wallet."
      },
      "PassTypeGoogleImageModule": {
        "type": "object",
        "properties": {
          "description": {
            "description": "What the image shows, read by screen readers. Carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "image": {
            "type": [
              "null",
              "string"
            ],
            "description": "The image."
          }
        },
        "additionalProperties": false,
        "description": "An image shown at full width among the details of the pass."
      },
      "PassTypeGoogleListTemplateInfo": {
        "type": "object",
        "properties": {
          "rows": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "One line of the card in the list of passes.",
              "$ref": "#/components/schemas/PassTypeGoogleListTemplateInfoRow"
            },
            "description": "The lines under the card's title. Only the first two are shown."
          }
        },
        "additionalProperties": false,
        "description": "How the card reads in the holder's list of passes."
      },
      "PassTypeGoogleListTemplateInfoRow": {
        "type": "object",
        "properties": {
          "paths": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Google field paths to read the line from. The first one holding a value is shown."
          }
        },
        "additionalProperties": false,
        "description": "One line of the card in the list of passes."
      },
      "PassTypeGoogleLoyaltyPoint": {
        "type": "object",
        "properties": {
          "balance": {
            "description": "The account holder's loyalty point balance, such as \"500\" or \"$10.00\". Recommended maximum length is\n7 characters. This is a required field of loyaltyPoints and secondaryLoyaltyPoints.",
            "$ref": "#/components/schemas/PassTypeGoogleBalanceConfigurationBase"
          },
          "label": {
            "description": "The loyalty points label, such as \"Points\". Recommended maximum length is 9 characters. Shown to the\npass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleMessage": {
        "type": "object",
        "properties": {
          "body": {
            "description": "The message body. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "displayInterval": {
            "description": "The period of time that the message will be displayed to users. You can define both a startTime and\nendTime for each message. A message is displayed immediately after a Wallet Object is inserted\nunless a startTime is set. The message will appear in a list of messages indefinitely if endTime is\nnot provided.",
            "$ref": "#/components/schemas/PassTypeGoogleTimeInterval"
          },
          "header": {
            "description": "The message header. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "id": {
            "type": [
              "null",
              "string"
            ],
            "description": "Optional identifier."
          },
          "notify": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Indicate if a notification should appear when the body change. See\nhttps://developers.google.com/wallet/retail/loyalty-cards/use-cases/trigger-push-notifications#add-message-and-notify-integration-steps\nfor more information."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleMoney": {
        "type": "object",
        "properties": {
          "currencyCode": {
            "type": [
              "null",
              "string"
            ],
            "description": "The currency code, such as \"USD\" or \"EUR.\"."
          },
          "value": {
            "type": [
              "null",
              "string"
            ],
            "description": "Amount, as a number or a Liquid template rendering one. Not a translatable string: one value for\nevery language."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleRow": {
        "type": "object",
        "properties": {
          "customRowLabel": {
            "description": "A custom label to use for the row value (eventTicketObject.seatInfo.row) on the card detail view.\nThis should only be used if the default \"Row\" label or one of the rowLabel options is not\nsufficient. Both rowLabel and customRowLabel may not be set. If neither is set, the label will\ndefault to \"Row\", localized. If the row field is unset, this label will not be used. This property\nis localizable. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "row": {
            "type": [
              "null",
              "string"
            ],
            "description": "The row of the seat, such as \"1\", E\", \"BB\", or \"A5\". This field is localizable so you may translate\nwords or use different alphabets for the characters in an identifier."
          },
          "rowLabel": {
            "type": [
              "null",
              "string"
            ],
            "description": "The label to use for the row value (eventTicketObject.seatInfo.row) on the card detail view. Each\navailable option maps to a set of localized strings, so that translations are shown to the user\nbased on their locale. Both rowLabel and customRowLabel may not be set. If neither is set, the label\nwill default to \"Row\", localized. If the row field is unset, this label will not be used. One of:\nROW_LABEL_UNSPECIFIED, ROW."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleSeat": {
        "type": "object",
        "properties": {
          "customSeatLabel": {
            "description": "A custom label to use for the seat value (eventTicketObject.seatInfo.seat) on the card detail view.\nThis should only be used if the default \"Seat\" label or one of the seatLabel options is not\nsufficient. Both seatLabel and customSeatLabel may not be set. If neither is set, the label will\ndefault to \"Seat\", localized. If the seat field is unset, this label will not be used. This property\nis localizable. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "seat": {
            "type": [
              "null",
              "string"
            ],
            "description": "The seat number, such as \"1\", \"2\", \"3\", or any other seat identifier. This field is localizable so\nyou may translate words or use different alphabets for the characters in an identifier."
          },
          "seatLabel": {
            "type": [
              "null",
              "string"
            ],
            "description": "The label to use for the seat value (eventTicketObject.seatInfo.seat) on the card detail view. Each\navailable option maps to a set of localized strings, so that translations are shown to the user\nbased on their locale. Both seatLabel and customSeatLabel may not be set. If neither is set, the\nlabel will default to \"Seat\", localized. If the seat field is unset, this label will not be used.\nOne of: SEAT_LABEL_UNSPECIFIED, SEAT."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleSection": {
        "type": "object",
        "properties": {
          "customSectionLabel": {
            "description": "A custom label to use for the section value (eventTicketObject.seatInfo.section) on the card detail\nview. This should only be used if the default \"Section\" label or one of the sectionLabel options is\nnot sufficient. Both sectionLabel and customSectionLabel may not be set. If neither is set, the\nlabel will default to \"Section\", localized. If the section field is unset, this label will not be\nused. This property is localizable. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "section": {
            "type": [
              "null",
              "string"
            ],
            "description": "The section of the seat, such as \"121\". This field is localizable so you may translate words or use\ndifferent alphabets for the characters in an identifier."
          },
          "sectionLabel": {
            "type": [
              "null",
              "string"
            ],
            "description": "The label to use for the section value (eventTicketObject.seatInfo.section) on the card detail view.\nEach available option maps to a set of localized strings, so that translations are shown to the user\nbased on their locale. Both sectionLabel and customSectionLabel may not be set. If neither is set,\nthe label will default to \"Section\", localized. If the section field is unset, this label will not\nbe used. One of: SECTION_LABEL_UNSPECIFIED, SECTION, THEATRE."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleSmartTap": {
        "type": "object",
        "properties": {
          "redemptionIssuers": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Identifies which redemption issuers can redeem the pass over Smart Tap. Redemption issuers are\nidentified by their issuer ID."
          },
          "value": {
            "type": [
              "null",
              "string"
            ],
            "description": "The value that will be transmitted to a Smart Tap certified terminal over NFC for this object. The\nfields enableSmartTap and redemptionIssuers must also be set up correctly in order for the pass to\nsupport Smart Tap. Only ASCII characters are supported. If this value is not set but the class level\nfields enableSmartTap and redemptionIssuers are set up correctly, the barcode.value or the accountId\nfields are used as fallback if present. A Liquid template, not a translatable string: one value for\nevery language."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleStampImage": {
        "type": "object",
        "properties": {
          "count": {
            "type": [
              "null",
              "integer"
            ],
            "description": "The stamp count this image is shown at.",
            "format": "int32"
          },
          "heroImage": {
            "type": [
              "null",
              "string"
            ],
            "description": "Hero image for that count (1032x336)."
          }
        },
        "additionalProperties": false,
        "description": "The Google image a stamp card shows at one exact stamp count."
      },
      "PassTypeGoogleTemplateOverride": {
        "type": "object",
        "properties": {
          "barcodeInfo": {
            "description": "The values shown around the barcode.",
            "$ref": "#/components/schemas/PassTypeGoogleBarcodeInfo"
          },
          "cardTemplateInfo": {
            "description": "The rows of values on the front of the card.",
            "$ref": "#/components/schemas/PassTypeGoogleCardTemplateInfo"
          },
          "detailsTemplateInfo": {
            "description": "The order and content of the details view.",
            "$ref": "#/components/schemas/PassTypeGoogleDetailsTemplateOverride"
          },
          "listTemplateInfo": {
            "description": "How the card reads in the holder's list of passes.",
            "$ref": "#/components/schemas/PassTypeGoogleListTemplateInfo"
          }
        },
        "additionalProperties": false,
        "description": "Which values the card shows where, in place of Google's default layout."
      },
      "PassTypeGoogleText": {
        "type": "object",
        "properties": {
          "body": {
            "description": "The body of the Text Module, which is defined as an uninterrupted string. Recommended maximum length\nis 500 characters to ensure full string is displayed on smaller screens. Shown to the pass holder,\nso it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "header": {
            "description": "The header of the Text Module. Recommended maximum length is 35 characters to ensure full string is\ndisplayed on smaller screens. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleTimeInterval": {
        "type": "object",
        "properties": {
          "end": {
            "type": [
              "null",
              "string"
            ],
            "description": "End time of the interval."
          },
          "start": {
            "type": [
              "null",
              "string"
            ],
            "description": "Start time of the interval."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleUri": {
        "type": "object",
        "properties": {
          "label": {
            "description": "The URI's title appearing in the app as text. Recommended maximum is 20 characters to ensure full\nstring is displayed on smaller screens. Shown to the pass holder, so it carries one value per\nlanguage.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "uri": {
            "type": [
              "null",
              "string"
            ],
            "description": "The location of a web page, image, or other resource. URIs in the LinksModuleData module can have\ndifferent prefixes indicating the type of URI (a link to a web page, a link to a map, a telephone\nnumber, or an email address). URIs must have a scheme. The type is a string because it can be a\ntemplated string. The templated string should return a valid Uri."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleValueAddedItem": {
        "type": "object",
        "properties": {
          "body": {
            "description": "Body to be displayed on the module. Character limit is 50 and longer strings will be truncated. This\nproperty is localizable. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "displayInterval": {
            "description": "The period of time that the module will be displayed to users. Can define both a startTime and\nendTime. The module is displayed immediately after insertion unless a startTime is set. The module\nis displayed indefinitely if endTime is not set.",
            "$ref": "#/components/schemas/PassTypeGoogleTimeInterval"
          },
          "header": {
            "description": "Header to be displayed on the module. Character limit is 60 and longer strings will be truncated.\nThis property is localizable. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "logo": {
            "type": [
              "null",
              "string"
            ],
            "description": "Image to be displayed on the module. Recommended image ratio is 1:1. Images will be resized to fit\nthis ratio."
          },
          "uri": {
            "type": [
              "null",
              "string"
            ],
            "description": "URI that the module leads to on click. This can be a web link or a deep link as mentioned in\nhttps://developer.android.com/training/app-links/deep-linking. The type is a string because it can\nbe a templated string. The templated string should return a valid Uri."
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleVenue": {
        "type": "object",
        "properties": {
          "address": {
            "description": "The address of the venue, such as \"24 Willie Mays Plaza\\nSan Francisco, CA 94107\". Address lines are\nseparated by line feed (\\n) characters. This propery is localizable. Shown to the pass holder, so it\ncarries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "name": {
            "description": "The name of the venue, such as \"AT&T Park\". This property is localizable. Shown to the pass\nholder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeGoogleWebAppLinkInfo": {
        "type": "object",
        "properties": {
          "targetUri": {
            "description": "URI for AppTarget. The description on the URI must be set. Prefer setting package field instead, if\nthis target is defined for your application.",
            "$ref": "#/components/schemas/PassTypeGoogleUri"
          }
        },
        "additionalProperties": false,
        "description": "Part of the Google configuration."
      },
      "PassTypeImageInfo": {
        "required": [
          "name",
          "path"
        ],
        "type": "object",
        "properties": {
          "path": {
            "type": "string",
            "description": "Path of the image. Use it verbatim as an image value in the template — for example as\n`apple.images.logo`."
          },
          "name": {
            "type": "string",
            "description": "File name of the image."
          }
        },
        "additionalProperties": false,
        "description": "A template image."
      },
      "PassTypeKind": {
        "enum": [
          "customerCard",
          "eventTicket",
          "giftCard",
          "offer",
          "generic",
          "stampCard"
        ],
        "type": "string",
        "description": "Which of the six templates a pass type is. Fixed when it is created."
      },
      "PassTypeListItem": {
        "required": [
          "appearance",
          "apple",
          "creationDate",
          "google",
          "image",
          "kind",
          "languages",
          "lastModificationDate",
          "metadata",
          "name",
          "tags"
        ],
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "Name of the template, unique within the tenant."
          },
          "tags": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "The labels the template is filed under. Empty when it carries none."
          },
          "creationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the template was created. Null when unknown. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "lastModificationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the template was last saved. Null when unknown. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "kind": {
            "description": "Which of the six templates this is, or null when the stored template cannot be read and needs\nrepairing.",
            "$ref": "#/components/schemas/PassTypeKind"
          },
          "apple": {
            "type": "boolean",
            "description": "Whether the template configures an Apple Wallet pass."
          },
          "google": {
            "type": "boolean",
            "description": "Whether the template configures a Google Wallet card."
          },
          "image": {
            "type": [
              "null",
              "string"
            ],
            "description": "The Apple image that best represents the template, exactly as configured — an image path such as\n`public/passes/loyalty/apple-strip.png`, or a remote URL. Null when the\ntemplate configures no Apple image at all."
          },
          "languages": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Languages this template has wording in, as language codes."
          },
          "appearance": {
            "description": "The colours the Apple card is drawn in, or null when the template configures no Apple half.",
            "$ref": "#/components/schemas/PassTypeAppearance"
          },
          "metadata": {
            "type": "array",
            "items": {
              "description": "One metadata field computed on every pass of the template.",
              "$ref": "#/components/schemas/PassTypeMetadataDefinition"
            },
            "description": "The metadata keys the template declares, which callers use to offer them as pass fields to filter\nand display on. Empty when the template declares none."
          }
        },
        "additionalProperties": false,
        "description": "A pass template as it appears in the list."
      },
      "PassTypeLocalizedString": {
        "type": "object",
        "properties": {
          "value": {
            "type": [
              "null",
              "string"
            ],
            "description": "Wording in the tenant's default language. Used for any language Neo.Web.Api.Wallet.Controllers.PassTypes.PassTypeLocalizedString.Values does not\ncover, so a pass is never blank."
          },
          "values": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "string"
            },
            "description": "Wording per language, keyed by language code — ISO 639-1, optionally with a region\n(`en`, `fr`, `fr-FR`). A language absent here falls back to Neo.Web.Api.Wallet.Controllers.PassTypes.PassTypeLocalizedString.Value."
          }
        },
        "additionalProperties": false,
        "description": "A value shown to the pass holder, in every language the tenant has written it in."
      },
      "PassTypeLocation": {
        "type": "object",
        "properties": {
          "latitude": {
            "type": [
              "null",
              "string"
            ],
            "description": "Latitude in degrees."
          },
          "longitude": {
            "type": [
              "null",
              "string"
            ],
            "description": "Longitude in degrees."
          }
        },
        "additionalProperties": false,
        "description": "An object that represents the coordinates of a location. See SemanticTagType.Location."
      },
      "PassTypeMetadata": {
        "type": "object",
        "properties": {
          "entries": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "One metadata field computed on every pass of the template.",
              "$ref": "#/components/schemas/PassTypeMetadataDefinition"
            },
            "description": "One entry per value computed."
          }
        },
        "additionalProperties": false,
        "description": "Values computed whenever a pass is updated, which issued passes can be searched by."
      },
      "PassTypeMetadataDefinition": {
        "type": "object",
        "properties": {
          "key": {
            "type": [
              "null",
              "string"
            ],
            "description": "Key of the value on each pass, and what passes are filtered on."
          },
          "type": {
            "type": [
              "null",
              "string"
            ],
            "description": "Data type of the value. One of: string, number, boolean, datetime. Omitted reads as string."
          },
          "value": {
            "type": [
              "null",
              "string"
            ],
            "description": "Liquid template computing the value whenever a pass is updated."
          }
        },
        "additionalProperties": false,
        "description": "One metadata field computed on every pass of the template."
      },
      "PassTypeModel": {
        "type": "object",
        "properties": {
          "kind": {
            "description": "Which of the six templates this is. Cannot be changed after creation.",
            "$ref": "#/components/schemas/PassTypeKind"
          },
          "tags": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Free-form labels the back office files this template under. Nothing here reaches the pass holder."
          },
          "creationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the template was created. Set by the platform on the first save and carried across every\nlater one; ignored on write. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "lastModificationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the template was last saved. Set by the platform on every save; ignored on write. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "passLayoutName": {
            "type": [
              "null",
              "string"
            ],
            "description": "Download page the template's passes are presented and installed from, by name. Omitted, the download\npage named `pass` is used. Must name an existing download page."
          },
          "trackLinks": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether links on the pass (back fields, messages, action links, Google links) go through a tracking\nredirect so that opening one can be counted. Omitted, links are tracked."
          },
          "optimizeImages": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether the images are optimized when a pass is built for Apple Wallet or Google Wallet. Omitted, they\nare. Images uploaded through the template image endpoint are optimized on upload whatever this says."
          },
          "notification": {
            "description": "How long a message sent to the template's passes stays displayed on them.",
            "$ref": "#/components/schemas/PassTypeNotification"
          },
          "previewData": {
            "type": [
              "null",
              "object"
            ],
            "description": "Sample values the editor renders the template's Liquid against, so a preview shows words rather\nthan expressions."
          },
          "extensions": {
            "description": "The two wallets and the sections that configure neither of them on its own.",
            "$ref": "#/components/schemas/PassTypeExtensions"
          }
        },
        "additionalProperties": false,
        "description": "Everything a pass template configures."
      },
      "PassTypeNotification": {
        "type": "object",
        "properties": {
          "duration": {
            "type": [
              "null",
              "string"
            ],
            "description": "How long a message sent to a pass of this template (through the notify endpoint) stays on it before it\nexpires, as a .NET `TimeSpan`, `d.hh:mm:ss` (`7.00:00:00` for a week, `00:05:00` for\nfive minutes)."
          }
        },
        "additionalProperties": false,
        "description": "How long a message sent to the template's passes stays displayed on them."
      },
      "PassTypePreview": {
        "type": "object",
        "properties": {
          "subTitle": {
            "description": "Sub title of the pass. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          },
          "title": {
            "description": "Title of the pass. Shown to the pass holder, so it carries one value per language.",
            "$ref": "#/components/schemas/PassTypeLocalizedString"
          }
        },
        "additionalProperties": false,
        "description": "Part of the pass configuration."
      },
      "PassTypeScannableData": {
        "type": "object",
        "properties": {
          "persistScannableData": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Specifies whether scannable data is kept on the pass. When enabled, the pass will include scannable\ndata that can be used by compatible systems."
          }
        },
        "additionalProperties": false,
        "description": "Part of the pass configuration."
      },
      "PassTypeStamps": {
        "type": "object",
        "properties": {
          "behaviour": {
            "type": [
              "null",
              "string"
            ],
            "description": "What happens to the card once `Target` is reached. One of: resetOnNextStamp, resetImmediately,\nstayAtGoal."
          },
          "rewardBenefitTemplateId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Identifier of the offer granted when the goal is reached, or `null` for a card that rewards\nnothing on its own."
          },
          "target": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Number of stamps that reaches the goal.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "The stamp mechanic carried by a `stampCard` pass: how many stamps reach the goal, what the card\nshows on the way there, and what happens once it arrives."
      },
      "PatchBenefitRequest": {
        "type": "object",
        "allOf": [
          {
            "$ref": "#/components/schemas/BenefitRequestBase"
          }
        ],
        "properties": {
          "type": {
            "description": "How the benefit is consumed. Omitted on an update, the current type is kept.",
            "$ref": "#/components/schemas/BenefitType"
          },
          "category": {
            "description": "What the benefit gives the holder. `GiftCard` is accepted for `MultiUse` only. Omitted on\nan update, the current category is kept.",
            "$ref": "#/components/schemas/BenefitCategory"
          },
          "passType": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of the benefit's standalone wallet pass. Null keeps the current one; an empty string\nunlinks it."
          },
          "options": {
            "description": "Additional processing options for benefit patching.",
            "$ref": "#/components/schemas/PatchOptions"
          }
        },
        "additionalProperties": false,
        "description": "Request model to patch an existing benefit."
      },
      "PatchOptions": {
        "type": "object",
        "properties": {
          "correlationId": {
            "maxLength": 100,
            "minLength": 10,
            "type": [
              "null",
              "string"
            ],
            "description": "The caller's own identifier for this call, e.g. a campaign run id, so support can find every call\nof one batch."
          },
          "notification": {
            "description": "The message to show the holder, in one or several languages.",
            "$ref": "#/components/schemas/NotifyRequest"
          }
        },
        "additionalProperties": false,
        "description": "Configuration options for benefit patching, including correlation tracking and notifications."
      },
      "PermissionAreaWeb": {
        "required": [
          "category",
          "code",
          "scopes"
        ],
        "type": "object",
        "properties": {
          "code": {
            "type": "string",
            "description": "Prefix shared by the scopes of the area, before the colon, e.g. `tenant.access`. Granting\n`{code}:*` grants every scope of the area."
          },
          "category": {
            "type": "string",
            "description": "Top-level category code used to group permission areas in the UI."
          },
          "description": {
            "type": [
              "null",
              "string"
            ],
            "description": "What the area covers, in English. Null when the area is undocumented."
          },
          "scopes": {
            "type": "array",
            "items": {
              "description": "One scope of a permission area.",
              "$ref": "#/components/schemas/PermissionScopeWeb"
            },
            "description": "Scopes of the area."
          }
        },
        "additionalProperties": false,
        "description": "A group of scopes sharing the same prefix."
      },
      "PermissionScopeWeb": {
        "required": [
          "code"
        ],
        "type": "object",
        "properties": {
          "code": {
            "type": "string",
            "description": "Part of the scope after the colon, e.g. `read`. The full scope granted to a role or an API key is\n`{area code}:{scope code}`, e.g. `tenant.access:read`."
          },
          "description": {
            "type": [
              "null",
              "string"
            ],
            "description": "What the scope allows, in English. Null when the scope is undocumented."
          }
        },
        "additionalProperties": false,
        "description": "One scope of a permission area."
      },
      "ProblemDetails": {
        "type": "object",
        "properties": {
          "type": {
            "type": [
              "null",
              "string"
            ]
          },
          "title": {
            "type": [
              "null",
              "string"
            ]
          },
          "status": {
            "type": [
              "null",
              "integer"
            ],
            "format": "int32"
          },
          "detail": {
            "type": [
              "null",
              "string"
            ]
          },
          "instance": {
            "type": [
              "null",
              "string"
            ]
          }
        },
        "additionalProperties": { }
      },
      "Profile": {
        "type": "object",
        "properties": {
          "email": {
            "type": [
              "null",
              "string"
            ],
            "description": "Email address of the profile; looks up the holder in the tenant's customer systems."
          },
          "phone_number": {
            "type": [
              "null",
              "string"
            ],
            "description": "Phone number of the profile; looks up the holder in the tenant's customer systems, alongside or\ninstead of `email`."
          }
        },
        "additionalProperties": false,
        "description": "The Klaviyo profile to synchronise, as a Klaviyo webhook sends it (snake_case names)."
      },
      "ProfileEventType": {
        "enum": [
          "Create",
          "Update"
        ],
        "type": "string",
        "description": "Profile table event Actito reports. The integration subscribes to both, the update one only for changes\nof the profile attribute named by `actitoExternalIdentifier`."
      },
      "PubSubConnection": {
        "type": "object",
        "properties": {
          "url": {
            "type": "string",
            "description": "WebSocket URL to connect to. Get a fresh one from `GET settings` to reconnect.",
            "format": "uri"
          }
        },
        "additionalProperties": false,
        "description": "Push channel of a device."
      },
      "PushUpdateData": {
        "required": [
          "identifiers"
        ],
        "type": "object",
        "properties": {
          "identifiers": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            },
            "description": "Identifies the one pass to update. Either `id` alone (the pass id), or one or more external\nidentifiers prefixed with `id.`, e.g. `{ \"id.customerId\": \"12345\" }`; a pass must match all of them."
          },
          "passType": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template to move the pass to. Must be declared for the tenant, or the request is refused with a 400.\nNull or omitted keeps the current pass template."
          },
          "additionalData": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "null"
            },
            "description": "Values merged into the pass's additional data, which pass templates and scripts read.\nKeys not sent keep their current value. Null or omitted changes nothing."
          },
          "updateMetadata": {
            "type": "boolean",
            "description": "When true, the update also re-reads the holder's data from the tenant's connected systems and\nrecomputes the stored pass metadata. Slower; leave false when the payload carries everything. Default false.",
            "default": false
          }
        },
        "additionalProperties": false,
        "description": "The pass a Klaviyo webhook targets and the change to apply to it."
      },
      "PushUpdateResult": {
        "type": "object",
        "properties": {
          "passCount": {
            "type": "integer",
            "description": "Passes matched by the filters and queued for the update; 0 when none matched.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "What a bulk update scheduled."
      },
      "PushUpdateStatistics": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Id of the progress record."
          },
          "operationName": {
            "type": "string",
            "description": "Name of the operation that first scheduled updates under this correlation id."
          },
          "operationData": {
            "type": "string",
            "description": "The correlation id: the value to pass to `POST pushUpdate/{correlationId}/cancel`."
          },
          "startDate": {
            "type": "string",
            "description": "When the first update was scheduled.",
            "format": "date-time"
          },
          "lastActivity": {
            "type": [
              "null",
              "string"
            ],
            "description": "When a pass of the operation last progressed; `null` before any did.",
            "format": "date-time"
          },
          "passCount": {
            "type": "integer",
            "description": "Pass updates scheduled under the operation.",
            "format": "int32"
          },
          "completed": {
            "type": "integer",
            "description": "Pass updates that finished, successfully or not.",
            "format": "int32"
          },
          "errors": {
            "type": "integer",
            "description": "Pass updates that failed.",
            "format": "int32"
          },
          "apple": {
            "type": "integer",
            "description": "Pass updates pushed to Apple devices.",
            "format": "int32"
          },
          "google": {
            "type": "integer",
            "description": "Pass updates sent to Google Wallet.",
            "format": "int32"
          },
          "isCanceled": {
            "type": "boolean",
            "description": "The operation was cancelled: its pass updates not yet run are skipped."
          }
        },
        "additionalProperties": false,
        "description": "Progress of one update operation: every pass update queued or applied under the same correlation id."
      },
      "QueryOptions": {
        "type": "object",
        "properties": {
          "maxRows": {
            "type": "integer",
            "description": "Most rows the query may return, between 1 and 100,000 (the default); outside that range the\ncall returns 400. A query that matches more rows returns 400 and no rows: aggregate or narrow\nit.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "Execution settings of a query."
      },
      "QueryRequest": {
        "required": [
          "query"
        ],
        "type": "object",
        "properties": {
          "query": {
            "type": "string",
            "description": "KQL query text. Only tables and columns of the analytics schema are accepted, and results only\ncover the tenant's own data; an empty query, invalid KQL or an unknown table or column returns 400\nwith a diagnostic."
          },
          "parameters": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            },
            "description": "Values for the query parameters, keyed by the name the query uses. Values are passed as KQL\nstrings. A name must start with a letter or `_` and contain only letters, digits and\n`_`; `params_tenantId` is reserved. Either violation returns 400."
          },
          "options": {
            "description": "Execution settings; omitted, the defaults apply.",
            "$ref": "#/components/schemas/QueryOptions"
          }
        },
        "additionalProperties": false,
        "description": "A KQL query to run over the tenant's analytics data."
      },
      "QueryResponse": {
        "type": "object",
        "properties": {
          "columns": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Column names, in the order the query projects them."
          },
          "rows": {
            "type": "array",
            "items": {
              "type": "array",
              "items": { }
            },
            "description": "One array per row, with one value per entry of Neo.Web.Api.Insights.Controllers.InsightsController.QueryResponse.Columns in the same order. An empty\ncell is `null`, a `dynamic` cell is its JSON value, a `bool` is a JSON boolean, and\ndates are UTC."
          }
        },
        "additionalProperties": false,
        "description": "Tabular result of a query."
      },
      "RedeemOnScanSettings": {
        "type": "object",
        "properties": {
          "repeatScanBlockSeconds": {
            "type": "integer",
            "description": "How long the device ignores a second scan of the same pass, 0 to 3600 seconds. 0 disables the block.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "Redemption behaviour when a pass is scanned."
      },
      "RenderTemplateRequest": {
        "required": [
          "templates"
        ],
        "type": "object",
        "properties": {
          "culture": {
            "type": [
              "null",
              "string"
            ],
            "description": "BCP 47 culture tag (`en`, `fr-FR`) the templates are rendered in: it drives date and number\nformatting and picks the language of localized values. Omitted or empty, `en-US` is used."
          },
          "templates": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Liquid templates to render, each independently of the others."
          },
          "context": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": { },
            "description": "Variables available to every template, by name. Nested objects and arrays are reachable with Liquid's\ndot and index syntax."
          }
        },
        "additionalProperties": false,
        "description": "Request body for rendering Liquid templates."
      },
      "RenderTemplateResponse": {
        "required": [
          "results"
        ],
        "type": "object",
        "properties": {
          "results": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Rendered outputs, trimmed of leading and trailing whitespace. `results[i]` is the output of\n`templates[i]`, or `null` when that template failed (see Neo.Web.Api.Template.Controllers.TemplatesController.RenderTemplateResponse.Errors)."
          },
          "errors": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Liquid error messages, aligned with Neo.Web.Api.Template.Controllers.TemplatesController.RenderTemplateResponse.Results; absent when every template rendered.\n`errors[i]` is `null` when `templates[i]` rendered."
          }
        },
        "additionalProperties": false,
        "description": "Response body returned by M:Neo.Web.Api.Template.Controllers.TemplatesController.Render(Neo.Web.Api.Template.Controllers.TemplatesController.RenderTemplateRequest,System.Threading.CancellationToken)."
      },
      "ResetResult": {
        "required": [
          "action",
          "correlationId",
          "taskId",
          "triggerType"
        ],
        "type": "object",
        "properties": {
          "taskId": {
            "type": "string",
            "description": "Id of the automation that was reset."
          },
          "triggerType": {
            "type": "string",
            "description": "Trigger type of the automation, which decided the reset: `dateRelative` or `fixedDate`."
          },
          "action": {
            "type": "string",
            "description": "`reset-and-backfill-enqueued` (dateRelative: runs not fired yet discarded, then a backfill started) or\n            `backfill-enqueued` (continuous fixedDate: a catch-up scan started, nothing discarded)."
          },
          "rowsDeleted": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Scheduled per-pass runs discarded because they had not fired yet; the backfill schedules again those\nstill due. `null` on a continuous fixedDate reset, which discards nothing.",
            "format": "int32"
          },
          "correlationId": {
            "type": "string",
            "description": "Correlation id of the backfill, the same on every reset of the automation. Its runs appear in the\nautomation's executions."
          }
        },
        "additionalProperties": false,
        "description": "What a reset did. The backfill it starts runs after the response is returned."
      },
      "RoleDefinition": {
        "required": [
          "name",
          "permissions"
        ],
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "Name of the role, as created; what a user's role refers to."
          },
          "permissions": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Permissions the role grants, resolved: an area wildcard (`area:*`) is expanded into the scopes of\nthat area enabled for the tenant, and a role holding `*` returns `[\"*\"]` alone."
          }
        },
        "additionalProperties": false,
        "description": "A role and the permissions it grants."
      },
      "RotatingBarcodeDefinition": {
        "required": [
          "digits",
          "hasSecret",
          "periodSeconds"
        ],
        "type": "object",
        "properties": {
          "hasSecret": {
            "type": "boolean",
            "description": "Whether a secret is set, so templates can use a rotating barcode. The secret itself is never returned."
          },
          "periodSeconds": {
            "type": "integer",
            "description": "How long one password stays valid, in seconds. 30 until configured.",
            "format": "int32"
          },
          "digits": {
            "type": "integer",
            "description": "Number of digits of a password. 8 until configured.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "Settings of rotating barcodes, which show a time-based one-time password. A scanner needs the secret,\nthe period and the digits."
      },
      "RotatingBarcodeSettings": {
        "type": "object",
        "properties": {
          "secret": {
            "type": "string",
            "description": "The tenant's secret for checking the passwords. Keep it on the device."
          },
          "periodSeconds": {
            "type": "integer",
            "description": "How long one password stays valid, in seconds.",
            "format": "int32"
          },
          "digits": {
            "type": "integer",
            "description": "The number of digits of a password.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "What a device needs to check the one-time passwords of Google Wallet rotating barcodes. The pass shows\nthe password where its barcode value holds `{totp_value_0}`."
      },
      "SaveDownloadPageLocalization": {
        "type": "object",
        "properties": {
          "resources": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Translation directories. Omitted keeps the current directories; provided replaces them, so an\nempty list clears them. Changing them does not move existing translations."
          },
          "translations": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "description": "Translated strings of one culture.",
              "$ref": "#/components/schemas/DownloadPageTranslations"
            },
            "description": "Translated strings to save, keyed by culture. Cultures left out are not touched. Omitted\nentirely, no translation is written."
          }
        },
        "additionalProperties": false,
        "description": "Localization wiring to write."
      },
      "SaveDownloadPageRequest": {
        "type": "object",
        "properties": {
          "type": {
            "description": "Kind of page. Required when the page does not exist yet. On an existing page it may be repeated\nbut not changed: a kind is fixed at creation.",
            "$ref": "#/components/schemas/DownloadPageType"
          },
          "headerImage": {
            "type": [
              "null",
              "string"
            ],
            "description": "Image shown in the header, as a URL. Omitted keeps the stored image; an empty string removes it."
          },
          "requireValidRedirectId": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether the page refuses traffic that does not come through a valid short link."
          },
          "autoDownloadPass": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether the pass is downloaded without the customer acting. `pass` pages only."
          },
          "passCreationFlow": {
            "type": [
              "null",
              "string"
            ],
            "description": "Flow executed when the page has to create the pass it shows. `pass` pages only. Omitted\nkeeps the stored flow; an empty string stops the page creating passes."
          },
          "allowDownloadAllPasses": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether a download-everything button is offered. `passList` and `benefitList` pages only."
          },
          "showInactivePasses": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether inactive passes are listed, undownloadable. `passList` pages only."
          },
          "localization": {
            "description": "Localization wiring and translations to store.",
            "$ref": "#/components/schemas/SaveDownloadPageLocalization"
          },
          "yaml": {
            "type": [
              "null",
              "string"
            ],
            "description": "The whole page as YAML, saved verbatim. Mutually exclusive with the typed fields, and must keep\nthe kind of page unchanged. Translations can still be sent alongside it."
          }
        },
        "additionalProperties": false,
        "description": "Request body to create or replace a download page."
      },
      "SaveEmailTemplateRequest": {
        "required": [
          "cultures"
        ],
        "type": "object",
        "properties": {
          "cultures": {
            "type": "object",
            "additionalProperties": {
              "description": "Design source and compiled content of a single template culture.",
              "$ref": "#/components/schemas/EmailTemplateCultureContent"
            },
            "description": "Content to upsert, keyed by culture code. Cultures not present in this map are left untouched. At least\none entry; each code 1 to 10 letters, digits, hyphens or underscores, else 400."
          }
        },
        "additionalProperties": false,
        "description": "Request body to save (create or update) culture content on an existing email template."
      },
      "SaveEnrolmentFormRequest": {
        "type": "object",
        "properties": {
          "flow": {
            "type": [
              "null",
              "string"
            ],
            "description": "Flow executed when a customer registers through this form. Required unless `yaml` is used, and\nmust name an existing registration flow, else 400."
          },
          "localization": {
            "description": "Localization wiring. Omitted keeps the stored resource directories; provided replaces them, so an\nempty list clears them.",
            "$ref": "#/components/schemas/EnrolmentFormLocalization"
          },
          "yaml": {
            "type": [
              "null",
              "string"
            ],
            "description": "Complete form as YAML, saved exactly as sent. Mutually exclusive with `flow` and\n`localization`, and must not be blank, else 400. The only way to save a form whose YAML no longer\nparses."
          }
        },
        "additionalProperties": false,
        "description": "Request body to save an existing enrolment form."
      },
      "SaveFlowRequest": {
        "required": [
          "steps"
        ],
        "type": "object",
        "properties": {
          "type": {
            "type": [
              "null",
              "string"
            ],
            "description": "Type of the flow. Must be a flow type available to the tenant, else 400. Omitted or blank keeps the\ncurrent type, or `userRegistration` when the flow has none."
          },
          "steps": {
            "type": "array",
            "items": {
              "description": "One step of a flow.",
              "$ref": "#/components/schemas/FlowStepDefinition"
            },
            "description": "Steps executed by the flow, in order. Replaces the stored steps entirely."
          }
        },
        "additionalProperties": false,
        "description": "Request body to save an existing flow."
      },
      "SavePassTypeRequest": {
        "required": [
          "configuration"
        ],
        "type": "object",
        "properties": {
          "configuration": {
            "description": "The template itself, in the same shape Neo.Web.Api.Wallet.Controllers.PassTypes.PassTypeDetail.Configuration returns. Send it\nwhole: a save replaces the stored template rather than merging into it, so anything left out is\nremoved, and wording left out is deleted in every language.",
            "$ref": "#/components/schemas/PassTypeModel"
          }
        },
        "additionalProperties": false,
        "description": "A pass template to create or replace."
      },
      "ScanFilter": {
        "type": "object",
        "properties": {
          "tags": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Tags of the benefit templates to accept. At most 50, each non-blank and at most 100 characters; trimmed\nand deduplicated on save."
          },
          "benefitTemplateIds": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Benefit templates to accept. At most 200, none blank; trimmed and deduplicated on save. An id that matches\nno benefit template is dropped and reported as a `benefitTemplateMissing` warning instead of refused."
          }
        },
        "additionalProperties": false,
        "description": "A benefit is accepted if it carries one of the tags or comes from one of the benefit templates. Both\nempty means every benefit is accepted."
      },
      "SchemaAssociation": {
        "type": "object",
        "properties": {
          "schema": {
            "type": "string",
            "description": "Title of the schema this rule selects."
          },
          "kind": {
            "description": "Which of the matching rules applies.",
            "$ref": "#/components/schemas/SchemaAssociationKind"
          },
          "path": {
            "type": "string",
            "description": "The exact file for Neo.Configuration.Tenants.Documentation.SchemaAssociationKind.File (e.g. `config.yml`), otherwise the folder\nprefix the file name must start with, trailing `/` included (e.g. `server/passes/`)."
          },
          "extension": {
            "type": [
              "null",
              "string"
            ],
            "description": "Suffix the file name must end with, dot included (e.g. `.yml`), for\nNeo.Configuration.Tenants.Documentation.SchemaAssociationKind.Prefix. Null accepts any file under Path."
          },
          "property": {
            "type": [
              "null",
              "string"
            ],
            "description": "Top-level property of the file carrying the discriminating value, for\nNeo.Configuration.Tenants.Documentation.SchemaAssociationKind.Discriminator; null otherwise."
          },
          "value": {
            "type": [
              "null",
              "string"
            ],
            "description": "String that property must hold, for Neo.Configuration.Tenants.Documentation.SchemaAssociationKind.Discriminator; null otherwise."
          }
        },
        "additionalProperties": false,
        "description": "The rule binding one schema to the files it validates. The same rules decide which schema a file is\nvalidated against when it is saved."
      },
      "SchemaAssociationKind": {
        "enum": [
          "File",
          "Prefix",
          "Discriminator"
        ],
        "type": "string",
        "description": "How a schema decides which configuration files it validates."
      },
      "ScriptEndpointSignature": {
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "The name `register` is called with, placeholders included."
          },
          "description": {
            "type": [
              "null",
              "string"
            ],
            "description": "What the endpoint is for, as its own documentation states it."
          },
          "methods": {
            "type": "array",
            "items": {
              "description": "One method of an endpoint, named as a script has to spell it.",
              "$ref": "#/components/schemas/ScriptMethodSignature"
            },
            "description": "The methods an implementation may carry."
          }
        },
        "additionalProperties": false,
        "description": "One endpoint a script may register an implementation for."
      },
      "ScriptMethodSignature": {
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "The property name an implementation is registered under."
          },
          "isOptional": {
            "type": "boolean",
            "description": "Whether the endpoint declares the method optional. A script may leave an optional method\nout; leaving out a required one changes what the platform can do."
          },
          "description": {
            "type": [
              "null",
              "string"
            ],
            "description": "What the method is for, as its own documentation states it."
          },
          "parameters": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "The parameter names, in order, for scaffolding a handler."
          }
        },
        "additionalProperties": false,
        "description": "One method of an endpoint, named as a script has to spell it."
      },
      "ScriptSlotUpdate": {
        "type": "object",
        "properties": {
          "content": {
            "type": [
              "null",
              "string"
            ],
            "description": "The new script content. Null deletes the file."
          }
        },
        "additionalProperties": false,
        "description": "A change to one script slot."
      },
      "ScriptTypings": {
        "type": "object",
        "properties": {
          "declarations": {
            "type": "string",
            "description": "The contents of a TypeScript declaration file describing `ScriptContext`. Types a\nscript that annotates its context parameter, down to the fields of every argument."
          },
          "endpoints": {
            "type": "array",
            "items": {
              "description": "One endpoint a script may register an implementation for.",
              "$ref": "#/components/schemas/ScriptEndpointSignature"
            },
            "description": "The same endpoints as data. A script cannot be made to carry that annotation, and\nTypeScript will not infer a parameter's type from the way it is used, so an editor also\nneeds the names on their own to complete `register(...)` without it."
          }
        },
        "additionalProperties": false,
        "description": "What an editor needs to help someone write an extensibility script."
      },
      "SecutixConfigurationResponse": {
        "required": [
          "connection",
          "pass",
          "rateLimit",
          "webhook"
        ],
        "type": "object",
        "properties": {
          "connection": {
            "description": "How the integration signs in to Secutix.",
            "$ref": "#/components/schemas/SecutixConnectionResponse"
          },
          "pass": {
            "description": "Pass template resolution and printing status settings.",
            "$ref": "#/components/schemas/SecutixPassSettings"
          },
          "webhook": {
            "description": "What an order change notification refreshes.",
            "$ref": "#/components/schemas/SecutixWebhookSettings"
          },
          "rateLimit": {
            "description": "Limit on calls to Secutix.",
            "$ref": "#/components/schemas/SecutixRateLimitSettings"
          }
        },
        "additionalProperties": false,
        "description": "The tenant's stored Secutix configuration, without the operator secret."
      },
      "SecutixConnectionRequest": {
        "required": [
          "institution",
          "operator",
          "url"
        ],
        "type": "object",
        "properties": {
          "url": {
            "type": "string",
            "description": "Base address of the tenant's Secutix back-end web services.",
            "format": "uri",
            "example": "https://xxx.pp-ws.secutix.com"
          },
          "institution": {
            "minLength": 1,
            "type": "string",
            "description": "Secutix institution code the integration acts for."
          },
          "operator": {
            "minLength": 1,
            "type": "string",
            "description": "Secutix operator (login) the integration acts as."
          },
          "partner": {
            "type": [
              "null",
              "string"
            ],
            "description": "Partner name registered in Secutix for the integration. Omitted or blank, the stored partner is kept, or\n`neostore` on a first save."
          },
          "secret": {
            "type": [
              "null",
              "string"
            ],
            "description": "Secret (password) of the Secutix operator. Omitted or blank, the stored secret is kept; with none stored,\nthe request is refused with 400. Never returned."
          }
        },
        "additionalProperties": false,
        "description": "Settings the integration uses to connect to Secutix."
      },
      "SecutixConnectionResponse": {
        "required": [
          "hasSecret",
          "institution",
          "operator",
          "partner",
          "url"
        ],
        "type": "object",
        "properties": {
          "url": {
            "type": "string",
            "description": "Base address of the tenant's Secutix back-end web services.",
            "format": "uri"
          },
          "institution": {
            "minLength": 1,
            "type": "string",
            "description": "Secutix institution code the integration acts for."
          },
          "operator": {
            "minLength": 1,
            "type": "string",
            "description": "Secutix operator (login) the integration acts as."
          },
          "partner": {
            "minLength": 1,
            "type": "string",
            "description": "Partner name registered in Secutix for the integration."
          },
          "hasSecret": {
            "type": "boolean",
            "description": "Whether an operator secret is stored. The secret itself is never returned; when true, a PUT may omit it."
          }
        },
        "additionalProperties": false,
        "description": "Settings the integration uses to connect to Secutix, without the operator secret."
      },
      "SecutixDefaultPassTypes": {
        "required": [
          "default"
        ],
        "type": "object",
        "properties": {
          "default": {
            "minLength": 1,
            "type": "string",
            "description": "Pass template of a ticket whose product family has no pass template of its own, or that has no product\nfamily."
          },
          "membership": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of a ticket of the Secutix `MEMBERSHIP` product family."
          },
          "seasonticket": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of a ticket of the Secutix `SEASONTICKET` product family."
          },
          "event": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of a ticket of the Secutix `SIMPLE_TICKET` product family."
          },
          "match": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of a ticket of the Secutix `SPORTING_EVENT` product family."
          },
          "visitPass": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of a ticket of the Secutix `VISIT_PASS` product family."
          },
          "openPass": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of a ticket of the Secutix `OPEN_PASS` product family."
          },
          "voucher": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of a ticket of the Secutix `VOUCHER` product family."
          },
          "donation": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of a ticket of the Secutix `DONATION` product family."
          },
          "service": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of a ticket of the Secutix `SERVICE` product family."
          },
          "openProduct": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template of a ticket of the Secutix `OPEN` product family."
          }
        },
        "additionalProperties": false,
        "description": "Fallback pass template of a Secutix ticket, per Secutix product family. Shared between the request and the\nresponse."
      },
      "SecutixPassSettings": {
        "required": [
          "defaultPassTypes"
        ],
        "type": "object",
        "properties": {
          "defaultPassTypes": {
            "description": "Fallback pass template per Secutix product family, for a ticket whose pass template is not otherwise\nresolved.",
            "$ref": "#/components/schemas/SecutixDefaultPassTypes"
          },
          "updatePrintingStatus": {
            "type": "boolean",
            "description": "Whether a ticket is marked as installed in its Secutix printing status when its pass is\nadded to a first wallet.",
            "default": false
          }
        },
        "additionalProperties": false,
        "description": "How passes are built from Secutix tickets. Shared between the request and the response."
      },
      "SecutixRateLimitSettings": {
        "type": "object",
        "properties": {
          "enabled": {
            "type": "boolean",
            "description": "Whether calls to Secutix are limited at all. Off, every call is sent.",
            "default": true
          },
          "permitLimit": {
            "maximum": 2147483647,
            "minimum": 1,
            "type": "integer",
            "description": "Maximum number of calls to Secutix per Neo.Extensions.Secutix.Controllers.SecutixRateLimitSettings.WindowSeconds. At least 1.",
            "format": "int32",
            "default": 400
          },
          "windowSeconds": {
            "maximum": 2147483647,
            "minimum": 1,
            "type": "integer",
            "description": "Length, in seconds, of the period Neo.Extensions.Secutix.Controllers.SecutixRateLimitSettings.PermitLimit applies to. At least 1.",
            "format": "int32",
            "default": 60
          },
          "retryAfterSeconds": {
            "maximum": 2147483647,
            "minimum": 0,
            "type": "integer",
            "description": "Default delay, in seconds, reported in `Retry-After` when a call is refused. 0 or more.",
            "format": "int32",
            "default": 60
          },
          "queueAcquireTimeoutSeconds": {
            "maximum": 2147483647,
            "minimum": 0,
            "type": "integer",
            "description": "Time, in seconds, a call over the limit may wait for a free slot before being refused. 0 refuses at once.",
            "format": "int32",
            "default": 0
          },
          "queueRetryDelaySeconds": {
            "maximum": 2147483647,
            "minimum": 1,
            "type": "integer",
            "description": "Interval, in seconds, at which a waiting call checks again for a free slot. At least 1.",
            "format": "int32",
            "default": 1
          }
        },
        "additionalProperties": false,
        "description": "Limit on the calls the integration makes to Secutix. Shared between the request and the response."
      },
      "SecutixScriptsDefinition": {
        "required": [
          "contactMapper",
          "contactPassUpdater",
          "movementMapper",
          "ticketPassTypeFinder"
        ],
        "type": "object",
        "properties": {
          "contactMapper": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          },
          "contactPassUpdater": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          },
          "movementMapper": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          },
          "ticketPassTypeFinder": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          }
        },
        "additionalProperties": false,
        "description": "The scripts the Secutix integration can be customised with."
      },
      "SecutixWebhookSettings": {
        "type": "object",
        "properties": {
          "searchForContactIds": {
            "type": "boolean",
            "description": "Whether an order change notification refreshes the passes of every movement and contact of the order,\nnot only the pass of the notified movement.",
            "default": false
          },
          "updateMetadata": {
            "type": "boolean",
            "description": "Whether a pass refreshed by an order change also has its data and pass template refreshed from Secutix.\nOff, the refresh is faster.",
            "default": true
          }
        },
        "additionalProperties": false,
        "description": "What an order change notification from Secutix refreshes. Shared between the request and the response."
      },
      "SetActitoRequest": {
        "required": [
          "actitoExternalIdentifier",
          "entity",
          "profileTableName",
          "server",
          "twcExternalIdentifier"
        ],
        "type": "object",
        "properties": {
          "server": {
            "type": "string",
            "description": "Root URL of the Actito API domain the entity lives on, e.g. `https://api3.actito.com`.",
            "format": "uri"
          },
          "entity": {
            "minLength": 1,
            "type": "string",
            "description": "Name of the Actito entity that holds the profile table, and in which the integration keeps its wallet\nand pass template tables, custom actions and webhook subscriptions."
          },
          "profileTableName": {
            "minLength": 1,
            "type": "string",
            "description": "Name of the Actito profile table the holders' profiles are read from."
          },
          "actitoExternalIdentifier": {
            "minLength": 1,
            "type": "string",
            "description": "Attribute of the profile table that carries the holder identifier shared with The Wallet Crew, e.g.\n`customerId`. Its value is matched against the pass identifier named by\nNeo.Extensions.Actito.Controllers.SetActitoRequest.TwcExternalIdentifier."
          },
          "twcExternalIdentifier": {
            "minLength": 1,
            "type": "string",
            "description": "Name of the pass identifier matched against Neo.Extensions.Actito.Controllers.SetActitoRequest.ActitoExternalIdentifier, e.g.\n`y2.customerId`. A pass without this identifier is never linked to an Actito profile."
          },
          "apiKey": {
            "type": [
              "null",
              "string"
            ],
            "description": "API key generated in the \"Manage API users\" page of the Actito portal. Never returned."
          }
        },
        "additionalProperties": false,
        "description": "Connection to the tenant's Actito entity, and how an Actito profile is matched to the holder's passes."
      },
      "SetActitoScriptsRequest": {
        "type": "object",
        "properties": {
          "profileMapper": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          }
        },
        "additionalProperties": false,
        "description": "Changes to the Actito scripts. A slot left out is left untouched."
      },
      "SetAparteRequest": {
        "required": [
          "baseUrl",
          "defaultPassType",
          "tenant",
          "timeZoneId"
        ],
        "type": "object",
        "properties": {
          "baseUrl": {
            "type": "string",
            "description": "Root URL of the Aparte WalletCrew API; must be an absolute `http` or `https` URL (else 400).\nReturned as sent.",
            "format": "uri"
          },
          "tenant": {
            "minLength": 1,
            "type": "string",
            "description": "Aparte tenant code, sent as the `X-Tenant` header of every call to Aparte. A value an HTTP\nheader cannot carry is refused with a 400."
          },
          "defaultPassType": {
            "minLength": 1,
            "type": "string",
            "description": "Pass template given to a pass created with an `aparte.ticketId` identifier and no pass template."
          },
          "invalidPassType": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template a ticket pass is moved to when, on a metadata update, Aparte no longer returns its\nticket. Null or omitted: the pass keeps its pass template."
          },
          "apiKey": {
            "type": [
              "null",
              "string"
            ],
            "description": "Aparte API key (the `X-Api-Key` header value Aparte issued). Never returned."
          },
          "timeZoneId": {
            "minLength": 1,
            "type": "string",
            "description": "IANA time zone of the venue, e.g. `Europe/Paris`; an unknown zone is refused with a 400."
          },
          "rateLimit": {
            "description": "Cap on the calls sent to Aparte. When omitted, the current settings are kept (500 per minute when none).",
            "$ref": "#/components/schemas/AparteRateLimitSettings"
          }
        },
        "additionalProperties": false,
        "description": "The Aparte configuration of the tenant, as sent on a save. Every field but `apiKey` and\n`rateLimit` is written as sent, so an omitted `invalidPassType` clears the stored one."
      },
      "SetAparteScriptsRequest": {
        "type": "object",
        "properties": {
          "ticketMapper": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          }
        },
        "additionalProperties": false,
        "description": "Changes to the Aparte scripts. A slot left out is left untouched."
      },
      "SetBloomreachCacheRequest": {
        "type": "object",
        "properties": {
          "customer": {
            "type": [
              "null",
              "string"
            ],
            "description": "How long a customer read from Bloomreach is reused before Bloomreach is asked again, as\n`d.hh:mm:ss`. Null, zero or negative turns the customer cache off.",
            "format": "date-span"
          }
        },
        "additionalProperties": false,
        "description": "How long Bloomreach lookups are reused."
      },
      "SetBloomreachRequest": {
        "required": [
          "apiKeyId",
          "baseUrl",
          "projectToken"
        ],
        "type": "object",
        "properties": {
          "projectToken": {
            "minLength": 1,
            "type": "string",
            "description": "Token of the Bloomreach project customers are read from and events are tracked into."
          },
          "baseUrl": {
            "type": "string",
            "description": "Root of the Bloomreach API. Must be an absolute http or https URL, otherwise 400. A path is kept, so a\nproxy prefix such as `https://proxy.example/bloomreach` works.",
            "format": "uri"
          },
          "apiKeyId": {
            "minLength": 1,
            "type": "string",
            "description": "Identifier of the Bloomreach API key (project settings > Access Management > API) whose secret is\nNeo.Extensions.Bloomreach.Controllers.SetBloomreachRequest.ApiKeySecret."
          },
          "apiKeySecret": {
            "type": [
              "null",
              "string"
            ],
            "description": "Secret of the API key. Never returned."
          },
          "cache": {
            "description": "How long Bloomreach lookups are reused. Omitted, the stored cache settings are kept; sent without a\nduration, caching is turned off.",
            "$ref": "#/components/schemas/SetBloomreachCacheRequest"
          }
        },
        "additionalProperties": false,
        "description": "Connection to the tenant's Bloomreach project, and how long customers read from it are reused."
      },
      "SetBloomreachScriptsRequest": {
        "type": "object",
        "properties": {
          "contactFinder": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          },
          "customerMapper": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          },
          "eventInterceptor": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          }
        },
        "additionalProperties": false,
        "description": "Changes to the Bloomreach scripts. A slot left out is left untouched."
      },
      "SetCegidY2Request": {
        "required": [
          "connections"
        ],
        "type": "object",
        "properties": {
          "connections": {
            "minItems": 1,
            "type": "array",
            "items": {
              "description": "One Y2 server connection, in the Cegid Y2 PUT request body.",
              "$ref": "#/components/schemas/CegidY2ConnectionRequest"
            },
            "description": "The complete list of Y2 server connections, at least one: a stored connection left out is removed. Names\nare unique and exactly one connection is the default, refused with 400 otherwise."
          },
          "updateCustomerOnPassInstallationChange": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether the Y2 customer is updated when the holder installs the pass on a first device or removes it from\nthe last one, so Y2 records whether the holder carries the pass. Omitted, the stored value is kept, or\ntrue when none is stored."
          },
          "cache": {
            "description": "Cache durations of the Y2 lookups. Omitted, the stored ones are kept; sent without durations, caching is\ndisabled.",
            "$ref": "#/components/schemas/CegidY2CacheSettings"
          },
          "rateLimit": {
            "description": "Client-side rate limiting. Omitted, the stored settings are kept, or the defaults when none are stored.",
            "$ref": "#/components/schemas/CegidY2RateLimitSettings"
          }
        },
        "additionalProperties": false,
        "description": "Request body for setting the Cegid Y2 configuration."
      },
      "SetCegidY2ScriptsRequest": {
        "type": "object",
        "properties": {
          "mapper": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          },
          "advisorRepository": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          },
          "connectionInterceptor": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          }
        },
        "additionalProperties": false,
        "description": "Changes to the Cegid Y2 scripts. A slot left out is left untouched."
      },
      "SetComarchRequest": {
        "required": [
          "connection",
          "providers"
        ],
        "type": "object",
        "properties": {
          "connection": {
            "description": "How the tenant reaches the Comarch API.",
            "$ref": "#/components/schemas/ComarchConnectionRequest"
          },
          "providers": {
            "description": "How the built-in customer and coupon providers behave.",
            "$ref": "#/components/schemas/ComarchProvidersConfiguration"
          },
          "kafkaConnection": {
            "description": "The Kafka topic to listen to. When omitted, the Kafka settings are removed and Comarch events stop being\nreceived; the stored Kafka password is kept, so switching Kafka back on does not ask for it again.",
            "$ref": "#/components/schemas/ComarchKafkaConnectionRequest"
          },
          "rateLimit": {
            "description": "Cap on the calls sent to Comarch. When omitted, the current settings are kept (80 per second when none).",
            "$ref": "#/components/schemas/ComarchRateLimitSettings"
          }
        },
        "additionalProperties": false,
        "description": "The Comarch configuration of the tenant, as sent on a save."
      },
      "SetComarchScriptsRequest": {
        "type": "object",
        "properties": {
          "customerMapper": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          },
          "locationMapper": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          },
          "walletInstallationCustomerUpdater": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          },
          "couponMapper": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          }
        },
        "additionalProperties": false,
        "description": "Changes to the Comarch scripts. A slot left out is left untouched."
      },
      "SetKlaviyoRequest": {
        "required": [
          "siteId"
        ],
        "type": "object",
        "properties": {
          "siteId": {
            "minLength": 1,
            "type": "string",
            "description": "Klaviyo public API key, also called site ID. Missing or empty is refused with a 400."
          },
          "listId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Klaviyo list the holder is subscribed to or unsubscribed from when the account's `consents_email`\n(and, with `enableSmsSupport`, `consents_sms`) consent is set."
          },
          "enableSmsSupport": {
            "type": "boolean",
            "description": "When true, the account's `consents_sms` consent is also synchronised to Klaviyo for the holder's\nphone number; when false, only the email consent is. Default false.",
            "default": false
          },
          "privateApiKey": {
            "type": [
              "null",
              "string"
            ],
            "description": "Klaviyo private API key. Never returned.\nOmitted, null or blank keeps the stored key; refused with a 400 when no key is stored yet."
          }
        },
        "additionalProperties": false,
        "description": "The Klaviyo connection of the tenant. A save replaces the stored configuration as a whole."
      },
      "SetKlaviyoScriptsRequest": {
        "type": "object",
        "properties": {
          "mapper": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          },
          "subscriptionsProvider": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          }
        },
        "additionalProperties": false,
        "description": "Changes to the Klaviyo scripts. A slot left out is left untouched."
      },
      "SetLanguageRequest": {
        "required": [
          "language"
        ],
        "type": "object",
        "properties": {
          "language": {
            "minLength": 1,
            "type": "string",
            "description": "Language code, one of the back-office languages the platform e-mails are translated into, e.g.\n`en` or `fr`. Also the language of the e-mails the platform sends this user."
          }
        },
        "additionalProperties": false,
        "description": "Request body to change the signed-in user's back-office language."
      },
      "SetMarketingCloudRequest": {
        "type": "object",
        "properties": {
          "signinKey": {
            "type": [
              "null",
              "string"
            ],
            "description": "JWT signing secret of the installed package (SFMC: Setup > Installed Packages) the Journey Builder\nactivities (Notify, Push Update) are configured with. Never returned."
          }
        },
        "additionalProperties": false,
        "description": "Salesforce Marketing Cloud settings of the tenant."
      },
      "SetRequest": {
        "required": [
          "value"
        ],
        "type": "object",
        "properties": {
          "value": {
            "type": "string",
            "description": "The secret value. Must not be empty or whitespace only."
          },
          "options": {
            "description": "Validity window of this value. Omitted or null, the value is readable at once and indefinitely.",
            "$ref": "#/components/schemas/OptionsRequest"
          }
        },
        "additionalProperties": false,
        "description": "Value of a secret and the window during which it can be read."
      },
      "SetSecutixRequest": {
        "required": [
          "connection",
          "pass"
        ],
        "type": "object",
        "properties": {
          "connection": {
            "description": "How the integration signs in to Secutix.",
            "$ref": "#/components/schemas/SecutixConnectionRequest"
          },
          "pass": {
            "description": "Pass template resolution and printing status settings. Stored as sent.",
            "$ref": "#/components/schemas/SecutixPassSettings"
          },
          "webhook": {
            "description": "What an order change notification refreshes. Omitted, the stored settings are kept, or the defaults on a\nfirst save.",
            "$ref": "#/components/schemas/SecutixWebhookSettings"
          },
          "rateLimit": {
            "description": "Limit on calls to Secutix. Omitted, the stored settings are kept, or the defaults on a first save.",
            "$ref": "#/components/schemas/SecutixRateLimitSettings"
          }
        },
        "additionalProperties": false,
        "description": "Secutix configuration to store for the tenant."
      },
      "SetSecutixScriptsRequest": {
        "type": "object",
        "properties": {
          "contactMapper": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          },
          "contactPassUpdater": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          },
          "movementMapper": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          },
          "ticketPassTypeFinder": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          }
        },
        "additionalProperties": false,
        "description": "Changes to the Secutix scripts. A slot left out is left untouched."
      },
      "SetShopifyRequest": {
        "required": [
          "shopifyUrl"
        ],
        "type": "object",
        "properties": {
          "shopifyUrl": {
            "minLength": 1,
            "type": "string",
            "description": "Shopify store URL, written as sent: either a bare host (`store.myshopify.com`) or a full URL\n(`https://store.myshopify.com`)."
          },
          "accessToken": {
            "type": [
              "null",
              "string"
            ],
            "description": "Shopify Admin API access token the integration reads and writes customers with. Never returned."
          }
        },
        "additionalProperties": false,
        "description": "Connection to the tenant's Shopify store."
      },
      "SetShopifyScriptsRequest": {
        "type": "object",
        "properties": {
          "customerMapper": {
            "description": "A change to one script slot.",
            "$ref": "#/components/schemas/ScriptSlotUpdate"
          }
        },
        "additionalProperties": false,
        "description": "Changes to the Shopify scripts. A slot left out is left untouched."
      },
      "SetTurnstileRequest": {
        "required": [
          "proofCookieValidityDurationSeconds",
          "siteKey"
        ],
        "type": "object",
        "properties": {
          "siteKey": {
            "minLength": 1,
            "type": "string",
            "description": "Public site key the customer web app renders the Turnstile widget with."
          },
          "secretKey": {
            "type": [
              "null",
              "string"
            ],
            "description": "Turnstile secret key of the widget. Never returned."
          },
          "proofCookieValidityDurationSeconds": {
            "maximum": 2147483647,
            "minimum": 0,
            "type": "integer",
            "description": "How long, in seconds, a browser that passed the challenge can create accounts again without a new\none. 0 requires a new challenge for every account creation.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "Cloudflare Turnstile settings. Once a site key is stored, every customer account creation must pass a\nTurnstile challenge."
      },
      "SftpFileResponse": {
        "required": [
          "blobPath",
          "fileName",
          "lastModified",
          "sizeInBytes",
          "status"
        ],
        "type": "object",
        "properties": {
          "fileName": {
            "type": "string",
            "description": "File name as the customer dropped it."
          },
          "status": {
            "type": "string",
            "description": "One of `pending`, `processed`, or `error`."
          },
          "sizeInBytes": {
            "type": "integer",
            "description": "File size in bytes.",
            "format": "int64"
          },
          "lastModified": {
            "type": "string",
            "description": "When the file was last written, in UTC.",
            "format": "date-time"
          },
          "blobPath": {
            "type": "string",
            "description": "Identifier of this file run, to pass to the import-log and download endpoints. Unique even when the\nsame file name is imported several times."
          }
        },
        "additionalProperties": false,
        "description": "One file sitting in the tenant's SFTP inbox."
      },
      "SftpImportLogResponse": {
        "required": [
          "fileRunFound",
          "passOutcomes",
          "status"
        ],
        "type": "object",
        "properties": {
          "status": {
            "type": "string",
            "description": "Current status of the file: `pending`, `processed`, or `error`."
          },
          "fileRunFound": {
            "type": "boolean",
            "description": "Whether an import run was found for the file. false while the file is pending."
          },
          "fileRunSuccess": {
            "type": [
              "null",
              "boolean"
            ],
            "description": "Whether the import itself completed successfully. null when not found."
          },
          "batchCount": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Number of batches the file was imported in.",
            "format": "int32"
          },
          "rowCount": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Total rows read from the file.",
            "format": "int32"
          },
          "successCount": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Rows that matched at least one pass, whose update was queued.",
            "format": "int32"
          },
          "noMatchCount": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Rows whose identifiers matched no pass at all — a data-quality signal, not a technical failure.",
            "format": "int32"
          },
          "errorCount": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Rows that failed to be processed.",
            "format": "int32"
          },
          "passOutcomes": {
            "type": "array",
            "items": {
              "description": "Outcome of a single pass touched by an imported file.",
              "$ref": "#/components/schemas/SftpPassOutcomeResponse"
            },
            "description": "Per-pass breakdown. Empty when no pass outcome is available yet."
          }
        },
        "additionalProperties": false,
        "description": "Full story of what happened when one SFTP-dropped file was imported."
      },
      "SftpPassOutcomeResponse": {
        "required": [
          "success"
        ],
        "type": "object",
        "properties": {
          "passId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Identifier of the pass, when known."
          },
          "success": {
            "type": "boolean",
            "description": "Whether the update of this pass, push to devices included, succeeded."
          },
          "errorMessage": {
            "type": [
              "null",
              "string"
            ],
            "description": "Failure reason. null on success or when none is known."
          }
        },
        "additionalProperties": false,
        "description": "Outcome of a single pass touched by an imported file."
      },
      "SftpStatusResponse": {
        "required": [
          "sftpEnabled"
        ],
        "type": "object",
        "properties": {
          "sftpEnabled": {
            "type": "boolean",
            "description": "false when the tenant has no SFTP inbox at all — the normal case for most\n            tenants, not an error. Every other field is null in that case."
          },
          "pendingCount": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Files dropped but not yet imported.",
            "format": "int32"
          },
          "processedCount": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Files imported without a technical failure.",
            "format": "int32"
          },
          "errorCount": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Files whose import failed.",
            "format": "int32"
          },
          "lastActivity": {
            "type": [
              "null",
              "string"
            ],
            "description": "Most recent write to any file, pending, processed or failed. Null when the inbox is empty.",
            "format": "date-time"
          }
        },
        "additionalProperties": false,
        "description": "Quick-glance SFTP activity summary for a tenant."
      },
      "ShopifyConfigurationResponse": {
        "required": [
          "hasAccessToken",
          "shopifyUrl"
        ],
        "type": "object",
        "properties": {
          "shopifyUrl": {
            "minLength": 1,
            "type": "string",
            "description": "Shopify store URL, as stored: a bare host or a full URL."
          },
          "hasAccessToken": {
            "type": "boolean",
            "description": "Whether an access token is stored. When true, a PUT may omit `accessToken` to keep it."
          }
        },
        "additionalProperties": false,
        "description": "The tenant's Shopify connection, without the access token."
      },
      "ShopifyScriptsDefinition": {
        "required": [
          "customerMapper"
        ],
        "type": "object",
        "properties": {
          "customerMapper": {
            "description": "The state of one script slot, as every extension's scripts endpoint returns it.",
            "$ref": "#/components/schemas/ExtensionScriptSlot"
          }
        },
        "additionalProperties": false,
        "description": "The scripts the Shopify integration can be customised with."
      },
      "SingleUpdatePassData": {
        "type": "object",
        "allOf": [
          {
            "description": "Changes to apply to an existing pass, with options.",
            "$ref": "#/components/schemas/UpdatePassData_SingleUpdatePassDataOptions"
          }
        ],
        "properties": {
          "bypassQueue": {
            "type": "boolean",
            "description": "Same as `options.bypassQueue`, which replaces it.",
            "default": false,
            "deprecated": true
          }
        },
        "additionalProperties": false,
        "description": "Changes to one pass. Omitted fields are left as they are."
      },
      "SingleUpdatePassDataOptions": {
        "type": "object",
        "allOf": [
          {
            "description": "How an update is applied.",
            "$ref": "#/components/schemas/UpdatePassDataOptions"
          }
        ],
        "properties": {
          "bypassQueue": {
            "type": "boolean",
            "description": "Applies the update and pushes it to the holder's devices within the request (200) instead of queuing\nit (202). Use it only when the change must show at once.",
            "default": false
          }
        },
        "additionalProperties": false,
        "description": "Options for a single pass update. Metadata is recomputed unless `updateMetadata` is `false`."
      },
      "SortModel": {
        "type": "object",
        "properties": {
          "field": {
            "type": "string",
            "description": "`id`, `passType`, `themeId`, `creationDate`, `lastUpdateDate`, `apple`,\n            `google` (installation data of that wallet), `identifiers.{key}` or `metadata.{key}`; a datetime\n            metadata field sorts chronologically. Any other field is refused with a 400."
          },
          "direction": {
            "description": "`ASC` or `DESC`.",
            "$ref": "#/components/schemas/SortModelDirection"
          }
        },
        "additionalProperties": false,
        "description": "One sort key for pass queries. Several keys apply in order, the first one being the primary sort."
      },
      "SortModelDirection": {
        "enum": [
          0,
          1
        ],
        "type": "integer",
        "description": "Sort direction for pass list queries, sent as `ASC` or `DESC`.",
        "format": "int32"
      },
      "StampCardResponse": {
        "type": "object",
        "properties": {
          "count": {
            "type": "integer",
            "description": "Stamps currently collected, the sum of every movement.",
            "format": "int32"
          },
          "target": {
            "type": "integer",
            "description": "Stamps needed to reach the goal, from the pass template's stamp configuration.",
            "format": "int32"
          },
          "behaviour": {
            "type": "string",
            "description": "What the card does once the goal is reached, from the pass template:\n`StayAtGoal` (the board stays full and refuses further stamps), `ResetImmediately` (the board\nclears in the same write that reaches the goal) or `ResetOnNextStamp` (the board stays full until the\nnext stamp clears it and starts a new round)."
          },
          "state": {
            "type": "string",
            "description": "`goalReached` when `count` is at or above `target`, otherwise `collecting`."
          },
          "movements": {
            "type": "array",
            "items": {
              "description": "One movement in a card's history.",
              "$ref": "#/components/schemas/StampMovementResponse"
            },
            "description": "Full history, oldest first, including the movements that cleared the board."
          },
          "rewardBenefitTemplateId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Benefit template granted on reaching the goal, or null when the pass template grants none.\nWhat the next goal will grant, not a record of what past goals did."
          }
        },
        "additionalProperties": false,
        "description": "The state of a stamp board."
      },
      "StampMovementResponse": {
        "type": "object",
        "properties": {
          "movementId": {
            "type": "string",
            "description": "Server-assigned identifier (GUID) of the movement."
          },
          "date": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When it was applied, in UTC. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "value": {
            "type": "integer",
            "description": "Signed change in stamps. The board clearing itself after a goal shows as a negative movement of the full count.",
            "format": "int32"
          },
          "source": {
            "type": [
              "null",
              "string"
            ],
            "description": "Identity of the caller (user or API key) that applied it; a clearing movement carries the source of the stamp that triggered it."
          },
          "remarks": {
            "type": [
              "null",
              "string"
            ],
            "description": "Note sent with the movement; clearing movements carry a system note."
          }
        },
        "additionalProperties": false,
        "description": "One movement in a card's history."
      },
      "StartSession": {
        "type": "object",
        "properties": {
          "profileId": {
            "type": "string",
            "description": "Profile to run: required, and one of the device's `profileIds`, otherwise 400."
          }
        },
        "additionalProperties": false,
        "description": "Profile a device starts running."
      },
      "Store": {
        "required": [
          "displayName",
          "storeId"
        ],
        "type": "object",
        "properties": {
          "storeId": {
            "type": "string",
            "description": "Identifier of the store in the tenant's store provider; the `storeId` the other store routes take."
          },
          "displayName": {
            "type": "string",
            "description": "Store name to show to staff and holders."
          },
          "availableLanguages": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Languages the store serves, as the store provider returns them; empty when the provider sets none."
          },
          "additionalResources": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": { },
            "description": "Store-specific texts, keyed by culture name; a culture with no text for this store is absent. Same\ncontent as `GET {storeId}/additionalResources`."
          },
          "additionalProperties": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": { },
            "description": "Free-form attributes the store provider attaches to the store; their keys depend on the provider."
          }
        },
        "additionalProperties": false,
        "description": "A physical store of the tenant, as supplied by the store provider configured for the tenant."
      },
      "StoreAdvisorDefinition": {
        "required": [
          "advisorId",
          "displayName"
        ],
        "type": "object",
        "properties": {
          "advisorId": {
            "type": "string",
            "description": "Identifier of the advisor (sales associate), as known to the retail system."
          },
          "displayName": {
            "type": "string",
            "description": "Name shown for the advisor."
          }
        },
        "additionalProperties": false,
        "description": "Advisor assigned to a store."
      },
      "StoreAdvisorRequest": {
        "required": [
          "advisorId",
          "displayName"
        ],
        "type": "object",
        "properties": {
          "advisorId": {
            "minLength": 1,
            "type": "string",
            "description": "Identifier of the advisor (sales associate), as known to the retail system."
          },
          "displayName": {
            "maxLength": 200,
            "minLength": 1,
            "type": "string",
            "description": "Name shown for the advisor, up to 200 characters."
          }
        },
        "additionalProperties": false,
        "description": "Advisor assigned to a store, as submitted through a store write request."
      },
      "StoreDefinition": {
        "required": [
          "latitude",
          "longitude",
          "storeId"
        ],
        "type": "object",
        "properties": {
          "storeId": {
            "type": "string",
            "description": "Identifier of the store, as known to the retail system; what a holder's `storeId` refers to."
          },
          "displayName": {
            "type": [
              "null",
              "string"
            ],
            "description": "Display name of the store. Null when none was given."
          },
          "address": {
            "type": [
              "null",
              "string"
            ],
            "description": "Postal address of the store, as free text. Null when none was given."
          },
          "longitude": {
            "type": "number",
            "description": "Longitude in decimal degrees. Used, with the latitude, to find the stores nearest a holder.",
            "format": "double"
          },
          "latitude": {
            "type": "number",
            "description": "Latitude in decimal degrees.",
            "format": "double"
          },
          "altitude": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Altitude in meters. Null when unknown.",
            "format": "int32"
          },
          "availableLanguages": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "ISO 639 codes of the languages spoken in the store, e.g. `fr`."
          },
          "advisors": {
            "type": "array",
            "items": {
              "description": "Advisor assigned to a store.",
              "$ref": "#/components/schemas/StoreAdvisorDefinition"
            },
            "description": "Advisors working in this store."
          },
          "additionalProperties": {
            "type": "object",
            "additionalProperties": { },
            "description": "Free-form values attached to the store, read by integrations, e.g. `y2.connectionName` for the\nCegid Y2 connection used for this store."
          }
        },
        "additionalProperties": false,
        "description": "Full definition of a store, returned by list/get/create/update endpoints."
      },
      "SubscriptionInformation": {
        "required": [
          "filters",
          "headers",
          "id",
          "name",
          "url",
          "user"
        ],
        "type": "object",
        "properties": {
          "enabled": {
            "type": "boolean",
            "description": "Whether Y2 currently delivers to this subscription. Registering this platform's subscription disables\nanother enabled one."
          },
          "id": {
            "type": "string",
            "description": "Y2 identifier of the subscription."
          },
          "name": {
            "type": "string",
            "description": "Name of the subscription in Y2."
          },
          "url": {
            "type": "string",
            "description": "URL Y2 posts the notifications to. For this platform's subscription, it ends with\n`/api/{tenantId}/webhooks/listeners/cegid/{connection name}`."
          },
          "headers": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            },
            "description": "HTTP headers Y2 adds to each notification, by name."
          },
          "user": {
            "description": "Credentials Y2 sends with each notification.",
            "$ref": "#/components/schemas/UserInformation"
          },
          "filters": {
            "type": "array",
            "items": {
              "description": "A Y2 rule selecting the notifications the subscription delivers or drops.",
              "$ref": "#/components/schemas/FilterInformation"
            },
            "description": "Rules selecting the notifications delivered; empty when Y2 has none."
          }
        },
        "additionalProperties": false,
        "description": "A Y2 business notification subscription: where Y2 sends its notifications for a database, and which ones."
      },
      "TOptions": {
        "type": "object",
        "properties": {
          "updateMetadata": {
            "type": "boolean",
            "description": "Recomputes and stores the pass metadata (the computed fields that filters and sorts read) along with the\nupdate. Slower; unnecessary when the update only changes what the pass displays. Defaults to `true`,\nexcept on a bulk update sent without a body."
          },
          "correlationId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Groups updates into one operation whose progress `GET pushUpdate/status` reports and\n`POST pushUpdate/{correlationId}/cancel` stops. A random id is used when omitted, except on a\nsynchronous update, which then records no progress."
          }
        },
        "additionalProperties": false
      },
      "TelemetrySettings": {
        "type": "object",
        "properties": {
          "minimumSeverity": {
            "description": "Lowest severity to send; anything below is dropped on the device and never uploaded.",
            "$ref": "#/components/schemas/DeviceTelemetrySeverity"
          },
          "maxBatchSize": {
            "type": "integer",
            "description": "Most items accepted in one telemetry upload. A larger batch is rejected.",
            "format": "int32"
          },
          "flushIntervalSeconds": {
            "type": "integer",
            "description": "How long the device buffers telemetry before uploading, in seconds.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "What and how much the device should report back."
      },
      "TenantConfigFaviconsWeb": {
        "required": [
          "rawFaviconUrl"
        ],
        "type": "object",
        "properties": {
          "faviconUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "Absolute URL to display the large (192x192) favicon from. When no large favicon is available, the\n`data:` URL of a warning icon instead."
          },
          "rawFaviconUrl": {
            "minLength": 1,
            "type": "string",
            "description": "Small (48x48) favicon URL as configured, for editing."
          },
          "rawLargeFaviconUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "Large (192x192) favicon URL as configured, for editing. Null when none is configured."
          },
          "rawAppleFaviconUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "Apple touch icon (180x180) URL as configured, for editing. Null when none is configured."
          }
        },
        "additionalProperties": false,
        "description": "Favicon URLs for tenant configuration response."
      },
      "TenantConfigWeb": {
        "required": [
          "availableLanguages",
          "defaultLanguage",
          "extensions",
          "favicons",
          "name",
          "publicUri"
        ],
        "type": "object",
        "properties": {
          "name": {
            "minLength": 1,
            "type": "string",
            "description": "Display name of the tenant. Not editable through this API."
          },
          "favicons": {
            "description": "The favicon as the back-office displays it, plus the three favicon paths as stored, for editing.",
            "$ref": "#/components/schemas/TenantConfigFaviconsWeb"
          },
          "logoUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "Logo URL of the tenant. Null when none is configured."
          },
          "appTitle": {
            "type": [
              "null",
              "string"
            ],
            "description": "Title that replaces the default application title in the browser. Null when none is configured."
          },
          "status": {
            "description": "Lifecycle status of the tenant. Null when none is set.",
            "$ref": "#/components/schemas/TenantStatus"
          },
          "purpose": {
            "description": "What the tenant is used for. Null when none is set.",
            "$ref": "#/components/schemas/TenantPurpose"
          },
          "publicUri": {
            "minLength": 1,
            "type": "string",
            "description": "Absolute base address holders are sent to (enrolment links, emails, QR codes): the tenant's\n`publicUri` when one is set, typically its custom domain, otherwise the platform's own address."
          },
          "defaultLanguage": {
            "minLength": 1,
            "type": "string",
            "description": "Fallback language of the tenant, one of Neo.Web.Api.Admin.Controllers.TenantConfigWeb.AvailableLanguages. `en` when none is configured."
          },
          "availableLanguages": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Languages the tenant's content is offered in, as language codes. `[\"en\"]` when none is configured."
          },
          "extensions": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Extensions enabled for the tenant. Empty when none is enabled."
          }
        },
        "additionalProperties": false,
        "description": "Tenant core configuration response"
      },
      "TenantConfigurationHistoryEntry": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Identifier of the stored configuration version."
          },
          "date": {
            "type": "string",
            "description": "When the version was saved.",
            "format": "date-time"
          },
          "user": {
            "description": "Who saved the version. Null when the save recorded no user.",
            "$ref": "#/components/schemas/TenantConfigurationHistoryUser"
          },
          "files": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Paths of the files this version added, changed or deleted compared with the version before it, sorted.\nEvery file of the version when no earlier version can be read; empty when this version's own details\ncannot be read."
          }
        },
        "additionalProperties": false,
        "description": "One saved version of the configuration: who saved it, when, and which files it changed."
      },
      "TenantConfigurationHistoryPage": {
        "type": "object",
        "properties": {
          "offset": {
            "type": "integer",
            "description": "Number of matching versions skipped before this page, as requested.",
            "format": "int32"
          },
          "limit": {
            "type": "integer",
            "description": "Maximum number of versions the page holds, as requested.",
            "format": "int32"
          },
          "total": {
            "type": "integer",
            "description": "Number of versions matching the request across all pages: every saved version without a file filter,\nonly those that changed a matching file with one. 0 when the tenant has no history.",
            "format": "int32"
          },
          "items": {
            "type": "array",
            "items": {
              "description": "One saved version of the configuration: who saved it, when, and which files it changed.",
              "$ref": "#/components/schemas/TenantConfigurationHistoryEntry"
            },
            "description": "The versions on this page, newest first. Fewer than Neo.Configuration.Tenants.TenantConfigurationHistoryPage.Limit on the last page."
          }
        },
        "additionalProperties": false,
        "description": "One page of the saved versions of a tenant's configuration, newest first."
      },
      "TenantConfigurationHistoryUser": {
        "type": "object",
        "properties": {
          "userName": {
            "type": [
              "null",
              "string"
            ],
            "description": "Identifier recorded with the version: the user id, or `apiKey:` followed by the API key name."
          },
          "name": {
            "type": [
              "null",
              "string"
            ],
            "description": "Display name: the user's name, or `API Key - ` followed by the key name. Null when the user no\nlonger exists."
          },
          "email": {
            "type": [
              "null",
              "string"
            ],
            "description": "The user's email. Null for an API key or a user that no longer exists."
          }
        },
        "additionalProperties": false,
        "description": "The user or API key behind a configuration version."
      },
      "TenantConfigurationVersionInformation": {
        "type": "object",
        "properties": {
          "version": {
            "type": "string",
            "description": "Opaque token for the configuration as a whole, Base64 of a hash over Neo.Configuration.Tenants.TenantConfigurationVersionInformation.Files. It changes\nwhenever any file is written, added or deleted, so two equal values mean the same configuration; empty\nwhen the tenant has no file.",
            "readOnly": true
          },
          "files": {
            "type": "object",
            "additionalProperties": {
              "type": "integer",
              "format": "int64"
            },
            "description": "Every configuration file, keyed by its path relative to the configuration root (e.g.\n`server/passes/loyalty.yml`), with a write stamp: the file's last modification time in Unix\nseconds, moved forward by one when two writes land in the same second, so it always increases."
          },
          "appliedMigrations": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Names of the configuration migrators already applied to this configuration. A migrator not listed here\nis still to be applied. A tenant whose version record had to be rebuilt is assumed to be up to\ndate and lists every migrator."
          }
        },
        "additionalProperties": false,
        "description": "Identifies one state of a tenant's whole configuration: which files exist and when each was last written."
      },
      "TenantDirectoryEntry": {
        "required": [
          "tenantId"
        ],
        "type": "object",
        "properties": {
          "tenantId": {
            "type": "string",
            "description": "Identifier of the tenant; the `tenantId` of every tenant-scoped route."
          },
          "status": {
            "description": "Lifecycle status of the tenant.",
            "$ref": "#/components/schemas/TenantDirectoryStatus"
          },
          "purpose": {
            "description": "Usage of the tenant.",
            "$ref": "#/components/schemas/TenantDirectoryPurpose"
          }
        },
        "additionalProperties": false,
        "description": "One tenant of the platform, as listed in the tenant directory."
      },
      "TenantDirectoryPurpose": {
        "enum": [
          "demo",
          "test",
          "production"
        ],
        "type": "string",
        "description": "What a tenant is used for, as set by `purpose` in its configuration. Informational."
      },
      "TenantDirectoryStatus": {
        "enum": [
          "onboarding",
          "active",
          "disabled"
        ],
        "type": "string",
        "description": "Lifecycle status of a tenant, as set by `status` in its configuration."
      },
      "TenantPurpose": {
        "enum": [
          "demo",
          "test",
          "production"
        ],
        "type": "string",
        "description": "What the tenant is used for. A label for the tenant directory and reporting: no runtime behaviour depends\non it."
      },
      "TenantStatus": {
        "enum": [
          "onboarding",
          "active",
          "disabled"
        ],
        "type": "string",
        "description": "Lifecycle stage of the tenant. Only `disabled` changes what the platform does; the other two values\nare labels."
      },
      "TenantUser": {
        "required": [
          "email",
          "id"
        ],
        "type": "object",
        "properties": {
          "id": {
            "minLength": 1,
            "type": "string",
            "description": "User id; the `userId` of the other user endpoints."
          },
          "email": {
            "minLength": 1,
            "type": "string",
            "description": "E-mail address the user signs in with. Shared by every tenant the account has access to."
          },
          "name": {
            "type": [
              "null",
              "string"
            ],
            "description": "Display name, shared by every tenant the account has access to. Null when none was given."
          },
          "blocked": {
            "type": "boolean",
            "description": "Whether the account is blocked, which prevents signing in to any tenant. Not settable here."
          },
          "lastLogin": {
            "type": [
              "null",
              "string"
            ],
            "description": "Last sign-in, to any tenant. Null when the user has never signed in, typically\nan invitation not yet used.",
            "format": "date-time"
          },
          "tenantRole": {
            "type": [
              "null",
              "string"
            ],
            "description": "Name of the role the user holds on this tenant, `administrator` for a tenant administrator. Null\nwhen the user holds no role."
          }
        },
        "additionalProperties": false,
        "description": "A back-office user, as seen from this tenant."
      },
      "ThemeAutomation": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Id of the automation, as used by the automation endpoints."
          },
          "displayName": {
            "type": [
              "null",
              "string"
            ],
            "description": "Name shown in the admin, `null` when the automation has none."
          }
        },
        "additionalProperties": false,
        "description": "An automation that applies a theme."
      },
      "ThemeImageInfo": {
        "type": "object",
        "properties": {
          "path": {
            "type": "string",
            "description": "Path of the image (`public/themes/{themeId}/{name}`), to put as is in an image location of this theme."
          },
          "name": {
            "type": "string",
            "description": "File name of the image, the `fileName` of the image endpoints."
          }
        },
        "additionalProperties": false,
        "description": "Reference to an uploaded theme image."
      },
      "ThemeInUse": {
        "required": [
          "automations",
          "passCount",
          "themeId"
        ],
        "type": "object",
        "properties": {
          "type": {
            "type": [
              "null",
              "string"
            ]
          },
          "title": {
            "type": [
              "null",
              "string"
            ]
          },
          "status": {
            "type": [
              "null",
              "integer"
            ],
            "format": "int32"
          },
          "detail": {
            "type": [
              "null",
              "string"
            ]
          },
          "instance": {
            "type": [
              "null",
              "string"
            ]
          },
          "themeId": {
            "type": "string",
            "description": "The theme that was asked to be deleted."
          },
          "passCount": {
            "type": "integer",
            "description": "How many passes still point at it.",
            "format": "int32"
          },
          "automations": {
            "type": "array",
            "items": {
              "description": "An automation that applies a theme.",
              "$ref": "#/components/schemas/ThemeAutomation"
            },
            "description": "The enabled automations still applying it."
          }
        },
        "additionalProperties": { },
        "description": "Problem returned when a theme still in use is deleted. These members extend the problem details."
      },
      "ThemeUsage": {
        "type": "object",
        "properties": {
          "themeId": {
            "type": "string",
            "description": "Id of the theme this usage is about."
          },
          "passCount": {
            "type": "integer",
            "description": "Number of passes currently pointing at it, `0` when none does.",
            "format": "int32"
          },
          "automations": {
            "type": "array",
            "items": {
              "description": "An automation that applies a theme.",
              "$ref": "#/components/schemas/ThemeAutomation"
            },
            "description": "Enabled automations applying it to passes, empty when none does."
          }
        },
        "additionalProperties": false,
        "description": "What points at one theme."
      },
      "TicketCanceledData": {
        "type": "object",
        "properties": {
          "ticket": {
            "description": "The cancelled ticket.",
            "$ref": "#/components/schemas/TicketData"
          }
        },
        "additionalProperties": false,
        "description": "Payload of a ticket cancellation."
      },
      "TicketCheckedData": {
        "type": "object",
        "properties": {
          "ticket": {
            "description": "The checked-in ticket.",
            "$ref": "#/components/schemas/TicketData"
          }
        },
        "additionalProperties": false,
        "description": "Payload of a ticket check-in."
      },
      "TicketData": {
        "type": "object",
        "properties": {
          "token": {
            "type": "string",
            "description": "Yurplan token of the ticket. With the event id it forms the pass identifier\n            `yurplan.ticketId`; it is exposed to the pass template as `barCode`."
          },
          "identifier": {
            "type": "string",
            "description": "Yurplan identifier of the ticket. Required; 400 when missing."
          }
        },
        "additionalProperties": false,
        "description": "A Yurplan ticket."
      },
      "TurnstileConfigurationResponse": {
        "required": [
          "siteKey"
        ],
        "type": "object",
        "properties": {
          "siteKey": {
            "minLength": 1,
            "type": "string",
            "description": "Public site key the customer web app renders the Turnstile widget with."
          },
          "proofCookieValidityDurationSeconds": {
            "type": "integer",
            "description": "How long, in seconds, a browser that passed the challenge can create accounts again without a new\none. 0: every account creation requires a new challenge.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "The tenant's Cloudflare Turnstile settings, without the secret key."
      },
      "TypeEnum": {
        "enum": [
          "manual",
          "text",
          "qrcode",
          "pdf417",
          "aztec",
          "code128",
          "code39",
          "codabar",
          "ean8",
          "ean13",
          "itf14",
          "upca",
          "datamatrix",
          "nfc"
        ],
        "type": "string",
        "description": "How the value was captured. Recorded on the scan event only; it does not affect matching."
      },
      "UpdateApiKeyRequest": {
        "required": [
          "enabled"
        ],
        "type": "object",
        "properties": {
          "enabled": {
            "type": "boolean",
            "description": "Whether requests authenticated with the key are accepted."
          },
          "permissions": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Permissions granted to the key, replacing the current ones: scopes, area wildcards (`area:*`) or\n`*` for full access. At least one is required."
          }
        },
        "additionalProperties": false,
        "description": "Request body to update an API key."
      },
      "UpdateAppleSignInRequest": {
        "required": [
          "serviceIdentifier"
        ],
        "type": "object",
        "properties": {
          "serviceIdentifier": {
            "minLength": 1,
            "type": "string",
            "description": "Apple Services ID on which \"Sign in with Apple\" is configured. The customer web app starts Sign in\nwith Apple with it. Missing or empty: 400."
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure sign in with Apple."
      },
      "UpdateAppleWalletProviderRequest": {
        "required": [
          "apnKey",
          "pass",
          "teamIdentifier"
        ],
        "type": "object",
        "properties": {
          "teamIdentifier": {
            "minLength": 1,
            "type": "string",
            "description": "Apple Developer Team ID that owns the pass type identifier."
          },
          "apnKey": {
            "description": "Key used to push pass updates to devices through the Apple Push Notification service.",
            "$ref": "#/components/schemas/APNKeyRequest"
          },
          "pass": {
            "description": "Pass type identifier and the certificate Apple passes are signed with.",
            "$ref": "#/components/schemas/PassRequest"
          },
          "webServiceUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "Web service URL written into every Apple pass generated from now on, which Apple Wallet calls to\nregister devices and fetch updates. Null means the platform's own endpoint,\n`/api/{tenantId}/passes/apple`.",
            "format": "uri"
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure Apple Wallet."
      },
      "UpdateCheckinPolicyRequest": {
        "required": [
          "mode"
        ],
        "type": "object",
        "properties": {
          "mode": {
            "description": "Policy to apply from now on, to every enrolment form of the tenant.",
            "$ref": "#/components/schemas/CheckinPolicyMode"
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure the check-in policy."
      },
      "UpdateDevice": {
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "description": "Name shown in the back office: required, at most 200 characters."
          },
          "description": {
            "type": [
              "null",
              "string"
            ],
            "description": "Free text for operators; null clears it."
          },
          "isEnabled": {
            "type": "boolean",
            "description": "Whether the device may connect; `false` when omitted. Disabling closes its running session."
          },
          "telemetry": {
            "description": "Telemetry settings; null leaves the device's current ones untouched.",
            "$ref": "#/components/schemas/UpdateTelemetrySettings"
          },
          "profileIds": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "type": "string"
            },
            "description": "Profiles the device can run, in the order it shows them; null leaves them untouched. Each must exist,\nbe of the device's type, and appear once."
          }
        },
        "additionalProperties": false,
        "description": "Payload to update a device."
      },
      "UpdateEmailProviderRequest": {
        "required": [
          "type"
        ],
        "type": "object",
        "properties": {
          "type": {
            "description": "Provider used to send mail. Changing it starts the provider settings afresh: the API key, the custom\nsending domain and any other setting of the previous provider are dropped.",
            "$ref": "#/components/schemas/EmailProviderType"
          },
          "from": {
            "description": "Sender identity. Required for `sendgrid` and `mailchimp`; not used by `script`.",
            "$ref": "#/components/schemas/FromRequest"
          },
          "apiKey": {
            "type": [
              "null",
              "string"
            ],
            "description": "API key of the provider. Omit or leave empty to keep the currently configured key, which is only\npossible when the provider type is left unchanged. Not used by `script`."
          },
          "script": {
            "type": [
              "null",
              "string"
            ],
            "description": "Content of the provider script, saved when `type` is `script`; omit or leave empty to keep\nthe currently configured script. The other provider types leave the script untouched."
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure the email provider."
      },
      "UpdateFacebookSignInRequest": {
        "required": [
          "appId"
        ],
        "type": "object",
        "properties": {
          "appId": {
            "minLength": 1,
            "type": "string",
            "description": "App ID of the Facebook app customers sign in through. The customer web app starts Facebook login with\nit. Missing or empty: 400."
          },
          "appSecret": {
            "type": [
              "null",
              "string"
            ],
            "description": "App secret of the Facebook app. Never returned."
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure sign in with Facebook."
      },
      "UpdateGeneralSecretsRequest": {
        "required": [
          "secret1",
          "secret2"
        ],
        "type": "object",
        "properties": {
          "secret1": {
            "minLength": 1,
            "type": "string",
            "description": "New signing secret, as in Neo.Web.Api.Admin.Controllers.Settings.SecurityController.GeneralSecretsDefinition.Secret1. Required and not empty."
          },
          "secret2": {
            "minLength": 1,
            "type": "string",
            "description": "New fallback secret, as in Neo.Web.Api.Admin.Controllers.Settings.SecurityController.GeneralSecretsDefinition.Secret2. Required and not empty."
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure the general secrets. Both values are replaced."
      },
      "UpdateGoogleSignInRequest": {
        "required": [
          "clientId"
        ],
        "type": "object",
        "properties": {
          "clientId": {
            "minLength": 1,
            "type": "string",
            "description": "OAuth client ID of the Google app customers sign in with. The customer web app starts Google sign-in\nwith it. Missing or empty: 400."
          },
          "gtmId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Google Tag Manager container the customer web app loads, e.g. `GTM-XXXX`."
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure sign in with Google."
      },
      "UpdateGoogleWalletProviderRequest": {
        "required": [
          "credential",
          "issuerId"
        ],
        "type": "object",
        "properties": {
          "issuerId": {
            "minLength": 1,
            "type": "string",
            "description": "Issuer ID from the Google Pay & Wallet Console; prefixes the ID of every Google pass class and object."
          },
          "credential": {
            "description": "Service account credential used to call the Google Wallet API.",
            "$ref": "#/components/schemas/CredentialRequest"
          },
          "webServiceUrl": {
            "type": [
              "null",
              "string"
            ],
            "description": "Callback URL Google Wallet notifies when a holder saves or removes a pass. Null means the platform's\nown endpoint, `/api/{tenantId}/passes/google`.",
            "format": "uri"
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure Google Wallet."
      },
      "UpdateLineSignInRequest": {
        "required": [
          "clientId"
        ],
        "type": "object",
        "properties": {
          "clientId": {
            "minLength": 1,
            "type": "string",
            "description": "Channel ID of the LINE Login channel customers sign in through (LINE Developers Console). The customer\nweb app starts LINE Login with it. Missing or empty: 400."
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure sign in with LINE."
      },
      "UpdatePassDataOptions": {
        "type": "object",
        "properties": {
          "updateMetadata": {
            "type": "boolean",
            "description": "Recomputes and stores the pass metadata (the computed fields that filters and sorts read) along with the\nupdate. Slower; unnecessary when the update only changes what the pass displays. Defaults to `true`,\nexcept on a bulk update sent without a body."
          },
          "correlationId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Groups updates into one operation whose progress `GET pushUpdate/status` reports and\n`POST pushUpdate/{correlationId}/cancel` stops. A random id is used when omitted, except on a\nsynchronous update, which then records no progress."
          }
        },
        "additionalProperties": false,
        "description": "How an update is applied."
      },
      "UpdatePassData_MultipleUpdatePassDataOptions": {
        "type": "object",
        "properties": {
          "identifiers": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            },
            "description": "Identifiers of the holder in other systems, keyed by system and field (`y2.customerId`,\n`shopify.customerId`). They are what `findPass`, `id.{key}` lookups and filters\nmatch on. Avoid keys starting with `id.`, the prefix lookups use."
          },
          "additionalData": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "null"
            },
            "description": "Free data stored with the pass and available to its templates (for example loyalty tier, store\ncode, campaign flags)."
          },
          "themeId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Theme applied to the pass, overriding the look of its pass template. Omit or send `null` to\nleave the current theme untouched (none on create); send an empty string to remove it. An id no\ndeclared theme has is refused with a 400."
          },
          "passType": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template to move the pass to; it then renders from that template. Omitted or blank, the pass\nkeeps its template. A name the tenant has no template for is refused with a 400."
          },
          "updateMetadata": {
            "type": "boolean",
            "description": "Same as `options.updateMetadata`, which replaces it.",
            "default": false,
            "deprecated": true
          },
          "options": {
            "description": "How the update is applied. Omitted, the defaults of each option apply.",
            "$ref": "#/components/schemas/MultipleUpdatePassDataOptions"
          }
        },
        "additionalProperties": false,
        "description": "Changes to apply to an existing pass, with options."
      },
      "UpdatePassData_SingleUpdatePassDataOptions": {
        "type": "object",
        "properties": {
          "identifiers": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            },
            "description": "Identifiers of the holder in other systems, keyed by system and field (`y2.customerId`,\n`shopify.customerId`). They are what `findPass`, `id.{key}` lookups and filters\nmatch on. Avoid keys starting with `id.`, the prefix lookups use."
          },
          "additionalData": {
            "type": [
              "null",
              "object"
            ],
            "additionalProperties": {
              "type": "null"
            },
            "description": "Free data stored with the pass and available to its templates (for example loyalty tier, store\ncode, campaign flags)."
          },
          "themeId": {
            "type": [
              "null",
              "string"
            ],
            "description": "Theme applied to the pass, overriding the look of its pass template. Omit or send `null` to\nleave the current theme untouched (none on create); send an empty string to remove it. An id no\ndeclared theme has is refused with a 400."
          },
          "passType": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template to move the pass to; it then renders from that template. Omitted or blank, the pass\nkeeps its template. A name the tenant has no template for is refused with a 400."
          },
          "updateMetadata": {
            "type": "boolean",
            "description": "Same as `options.updateMetadata`, which replaces it.",
            "default": false,
            "deprecated": true
          },
          "options": {
            "description": "How the update is applied. Omitted, the defaults of each option apply.",
            "$ref": "#/components/schemas/SingleUpdatePassDataOptions"
          }
        },
        "additionalProperties": false,
        "description": "Changes to apply to an existing pass, with options."
      },
      "UpdatePassData_TOptions": {
        "type": "object",
        "allOf": [
          {
            "$ref": "#/components/schemas/PassData"
          }
        ],
        "properties": {
          "passType": {
            "type": [
              "null",
              "string"
            ],
            "description": "Pass template to move the pass to; it then renders from that template. Omitted or blank, the pass\nkeeps its template. A name the tenant has no template for is refused with a 400."
          },
          "updateMetadata": {
            "type": "boolean",
            "description": "Same as `options.updateMetadata`, which replaces it.",
            "default": false,
            "deprecated": true
          },
          "options": {
            "description": "How the update is applied. Omitted, the defaults of each option apply.",
            "$ref": "#/components/schemas/TOptions"
          }
        },
        "additionalProperties": false,
        "description": "Changes to apply to an existing pass, with options."
      },
      "UpdateRoleRequest": {
        "required": [
          "permissions"
        ],
        "type": "object",
        "properties": {
          "permissions": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Permissions granted by the role, replacing the current ones: scopes, area wildcards (`area:*`) or\n`*` for full access. At least one is required."
          }
        },
        "additionalProperties": false,
        "description": "Request body to update a role's permissions."
      },
      "UpdateRotatingBarcodeRequest": {
        "required": [
          "digits",
          "periodSeconds"
        ],
        "type": "object",
        "properties": {
          "secret": {
            "type": [
              "null",
              "string"
            ],
            "description": "Any string, kept secret. Required the first time; omit it to keep the current one. Changing it\ninvalidates the codes every pass shows until the passes are updated."
          },
          "periodSeconds": {
            "maximum": 3600,
            "minimum": 1,
            "type": "integer",
            "description": "How long one password stays valid, in seconds, from 1 to 3600.",
            "format": "int32"
          },
          "digits": {
            "maximum": 10,
            "minimum": 6,
            "type": "integer",
            "description": "Number of digits of a password, from 6 to 10.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "Request body to configure rotating barcodes."
      },
      "UpdateStoreRequest": {
        "required": [
          "latitude",
          "longitude"
        ],
        "type": "object",
        "properties": {
          "displayName": {
            "maxLength": 200,
            "type": [
              "null",
              "string"
            ],
            "description": "Display name of the store, up to 200 characters. Omitted or null clears it."
          },
          "address": {
            "type": [
              "null",
              "string"
            ],
            "description": "Postal address of the store, as free text. Omitted or null clears it."
          },
          "longitude": {
            "maximum": 180,
            "minimum": -180,
            "type": "number",
            "description": "Longitude in decimal degrees, between -180 and 180, else 400.",
            "format": "double"
          },
          "latitude": {
            "maximum": 90,
            "minimum": -90,
            "type": "number",
            "description": "Latitude in decimal degrees, between -90 and 90, else 400.",
            "format": "double"
          },
          "altitude": {
            "type": [
              "null",
              "integer"
            ],
            "description": "Altitude in meters. Omitted or null clears it.",
            "format": "int32"
          },
          "availableLanguages": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "ISO 639 codes of the languages spoken in the store. Omitted means none."
          },
          "advisors": {
            "type": "array",
            "items": {
              "description": "Advisor assigned to a store, as submitted through a store write request.",
              "$ref": "#/components/schemas/StoreAdvisorRequest"
            },
            "description": "Advisors working in this store, replacing the current ones. Omitted means none."
          },
          "additionalProperties": {
            "type": "object",
            "additionalProperties": { },
            "description": "Free-form values attached to the store, read by integrations, e.g. `y2.connectionName`. Omitted\nmeans none."
          }
        },
        "additionalProperties": false,
        "description": "Request body to update a store. Fully replaces the store's fields other than its identifier."
      },
      "UpdateTelemetrySettings": {
        "type": "object",
        "properties": {
          "minimumSeverity": {
            "description": "Lowest severity the device should send. Setting it above everything the device emits silences it.",
            "$ref": "#/components/schemas/DeviceTelemetrySeverity"
          },
          "flushIntervalSeconds": {
            "type": "integer",
            "description": "How long the device buffers before uploading, 5 to 3600 seconds; outside that range returns 400.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "Telemetry settings an operator may change for a device."
      },
      "UpdateTenantUserRequest": {
        "required": [
          "role"
        ],
        "type": "object",
        "properties": {
          "name": {
            "maxLength": 200,
            "type": [
              "null",
              "string"
            ],
            "description": "New display name, up to 200 characters. Omitted or null keeps the current one. The name belongs to\nthe account, so it changes on every tenant the user has access to."
          },
          "role": {
            "minLength": 1,
            "type": "string",
            "description": "Name of the role to hold on this tenant, replacing the current one: `administrator` or one of\nthe tenant's roles, matched case-insensitively, else 400."
          }
        },
        "additionalProperties": false,
        "description": "Request payload for updating a tenant user."
      },
      "UpsertBenefitResponse": {
        "type": "object",
        "properties": {
          "benefitId": {
            "type": "string",
            "description": "Id of the benefit written - the existing one when the POST upserted on its origin. Use it for later\nPUT and movement calls."
          }
        },
        "additionalProperties": false,
        "description": "Response payload after a benefit is created or updated via POST."
      },
      "UpsertDeviceProfile": {
        "type": "object",
        "properties": {
          "type": {
            "description": "Device type the profile is for. Changing it on an update returns 400.",
            "$ref": "#/components/schemas/DeviceType"
          },
          "name": {
            "type": "string",
            "description": "Name shown to staff on the device: required, at most 200 characters, trimmed."
          },
          "description": {
            "type": [
              "null",
              "string"
            ],
            "description": "Free text for operators, at most 500 characters; blank is stored as none."
          },
          "emoji": {
            "type": [
              "null",
              "string"
            ],
            "description": "Icon shown next to the name, at most 16 characters; blank is stored as none."
          },
          "color": {
            "type": [
              "null",
              "string"
            ],
            "description": "Hex colour, `#rrggbb`; any other format returns 400, blank is stored as none."
          },
          "validFrom": {
            "type": [
              "null",
              "string"
            ],
            "description": "First instant the profile can be used, stored in UTC. Null means no start.",
            "format": "date-time"
          },
          "validUntil": {
            "type": [
              "null",
              "string"
            ],
            "description": "Instant the profile stops being usable, stored in UTC; must be after ValidFrom (the error is reported on `validFrom`). Null means no end.",
            "format": "date-time"
          },
          "schedule": {
            "type": [
              "null",
              "array"
            ],
            "items": {
              "description": "An opening window of a profile: it opens at every occurrence of Cron and stays open\nfor DurationMinutes.",
              "$ref": "#/components/schemas/DeviceProfileWindow"
            },
            "description": "Opening windows, at most 20. Null or empty means open all the time within the validity dates."
          },
          "settings": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/CrewCheckProfileSettings"
              }
            ],
            "description": "Type-specific settings; their type must match Type."
          },
          "id": {
            "type": [
              "null",
              "string"
            ],
            "description": "Stable identifier, required on create and ignored on update, where the route names the profile.\nLetters, digits, `_` and `-`, starting with a letter or digit, at most 128 characters."
          }
        },
        "additionalProperties": false,
        "description": "Payload to create or update a profile."
      },
      "UserInformation": {
        "type": "object",
        "properties": {
          "userName": {
            "type": [
              "null",
              "string"
            ],
            "description": "User Y2 authenticates the delivery with; empty when none."
          }
        },
        "additionalProperties": false,
        "description": "Credentials Y2 sends with each notification."
      },
      "WatchRequest": {
        "type": "object",
        "properties": {
          "sessionId": {
            "type": "string",
            "description": "Session returned by `connect`."
          }
        },
        "additionalProperties": false,
        "description": "Request body to keep a watcher session alive."
      },
      "WebClaim": {
        "type": "object",
        "properties": {
          "type": {
            "type": "string",
            "description": "Claim name as it appears in the token, for instance `email` or a customer directory field."
          },
          "value": {
            "type": "string",
            "description": "Claim value, as text."
          },
          "valueType": {
            "type": [
              "null",
              "string"
            ],
            "description": "Type of the value as a claim value-type URI (for instance `http://www.w3.org/2001/XMLSchema#integer`); null means string."
          }
        },
        "additionalProperties": false,
        "description": "One claim to put in a generated token."
      },
      "WebHook": {
        "required": [
          "endpoint",
          "events"
        ],
        "type": "object",
        "properties": {
          "description": {
            "type": [
              "null",
              "string"
            ],
            "description": "Free text to tell subscriptions apart; not used by the platform. Omitted on an update, the current\ndescription is cleared."
          },
          "events": {
            "minItems": 1,
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Event names that trigger a delivery. An entry matches its exact event name, or every event name\nstarting with what precedes a trailing `*` (`pass.*`; `*` alone matches every event).\nA `*` anywhere else is taken literally."
          },
          "endpoint": {
            "type": "string",
            "description": "URL that receives each matching event as a JSON `POST`, with the headers\n`X-NEOSTORE-TENANTID`, `X-NEOSTORE-EVENTNAME` and `X-NEOSTORE-SIGNATURE`.",
            "format": "uri"
          },
          "enabled": {
            "type": "boolean",
            "description": "Whether events are delivered. A disabled subscription is kept but receives nothing. Defaults to\n`false`, including when omitted on an update.",
            "default": false
          }
        },
        "additionalProperties": false,
        "description": "The caller-editable part of a webhook subscription."
      },
      "WebHookWithId": {
        "required": [
          "id",
          "signatureSecret"
        ],
        "type": "object",
        "allOf": [
          {
            "description": "The caller-editable part of a webhook subscription.",
            "$ref": "#/components/schemas/WebHook"
          }
        ],
        "properties": {
          "id": {
            "minLength": 1,
            "type": "string",
            "description": "Identifier the platform assigns on creation. It never changes and is the `id` the other\nwebhook routes take."
          },
          "signatureSecret": {
            "minLength": 1,
            "type": "string",
            "description": "Secret the platform generates on creation to sign every delivery.\nIt never changes, not even on an update."
          }
        },
        "additionalProperties": false,
        "description": "A webhook subscription as stored, with the values the platform generated for it."
      },
      "WebRedirectEntity": {
        "required": [
          "id",
          "layout",
          "uri"
        ],
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Case-sensitive alphanumeric code generated on create. It is the last segment of\nNeo.Web.Redirect.Controllers.WebRedirectEntity.Uri and the key of every other short URL endpoint."
          },
          "layout": {
            "type": "string",
            "description": "Page of the tenant's web app the visitor lands on: the short URL redirects to\n`{publicUrl}/{tenantId}/{layout}`."
          },
          "creationDate": {
            "oneOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "integer",
                "format": "int64"
              }
            ],
            "description": "When the short URL was created, in UTC. Kept unchanged by an update. Accepts ISO 8601 date-time string or Unix epoch seconds in request inputs. Responses are serialized as ISO 8601 date-time strings."
          },
          "parameters": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            },
            "description": "Query string parameters added to the layout URL on every visit."
          },
          "options": {
            "description": "Label and expiration date of the short URL.",
            "$ref": "#/components/schemas/WebRedirectOptions"
          },
          "uri": {
            "type": "string",
            "description": "The short URL to share: the platform's redirect domain followed by Neo.Web.Redirect.Controllers.WebRedirectEntity.Id. A visit redirects\n(302) to the layout and emits a redirected event; an unknown id answers 404."
          }
        },
        "additionalProperties": false,
        "description": "A short URL of the tenant and the page it redirects to."
      },
      "WebRedirectOptions": {
        "type": "object",
        "properties": {
          "expirationDate": {
            "type": [
              "null",
              "string"
            ],
            "description": "Expiration date of the short URL, for information. `null` means none.",
            "format": "date-time"
          },
          "label": {
            "type": [
              "null",
              "string"
            ],
            "description": "Free-text name that helps an admin recognise the short URL in the list. Never shown to the visitor.\nOmitted on an update, the stored label is cleared."
          },
          "length": {
            "type": "integer",
            "description": "Number of characters of the generated short URL id. Defaults to `6`.",
            "format": "int32"
          }
        },
        "additionalProperties": false,
        "description": "Optional settings of a short URL."
      },
      "WebhookRequest_OrderConfirmedData": {
        "type": "object",
        "properties": {
          "data": {
            "description": "The payload, under `data`. Required; 400 when missing.",
            "$ref": "#/components/schemas/OrderConfirmedData"
          }
        },
        "additionalProperties": false,
        "description": "Envelope of a Yurplan webhook call."
      },
      "WebhookRequest_TicketCanceledData": {
        "type": "object",
        "properties": {
          "data": {
            "description": "The payload, under `data`. Required; 400 when missing.",
            "$ref": "#/components/schemas/TicketCanceledData"
          }
        },
        "additionalProperties": false,
        "description": "Envelope of a Yurplan webhook call."
      },
      "WebhookRequest_TicketCheckedData": {
        "type": "object",
        "properties": {
          "data": {
            "description": "The payload, under `data`. Required; 400 when missing.",
            "$ref": "#/components/schemas/TicketCheckedData"
          }
        },
        "additionalProperties": false,
        "description": "Envelope of a Yurplan webhook call."
      }
    },
    "parameters": {
      "tenantId": {
        "name": "tenantId",
        "in": "path",
        "description": "Tenant identifier",
        "required": true,
        "schema": {
          "type": "string"
        }
      }
    },
    "securitySchemes": {
      "neo-customer": {
        "type": "http",
        "description": "a JWT token describing the customer",
        "scheme": "bearer"
      },
      "apiKey": {
        "type": "apiKey",
        "name": "X-API-KEY",
        "in": "header"
      },
      "admin-bearer": {
        "type": "oauth2",
        "flows": {
          "implicit": {
            "authorizationUrl": "https://auth.neostore.cloud/authorize?audience=https://app.neostore.cloud/api/",
            "scopes": { }
          }
        }
      }
    }
  },
  "tags": [
    {
      "name": "Pass Management",
      "description": "The core of The Wallet Crew API. These endpoints let you issue, read, update, and manage digital passes across Apple Wallet and Google Wallet — and record the real-world events that drive your loyalty, ticketing, and membership workflows.\n\n## Pass\n\nThe `Pass` tag covers the full lifecycle of a wallet pass.\n\n| Operation | Description |\n|-----------|-------------|\n| `GET /api/{tenantId}/passes` | List passes with filtering, sorting, and pagination. Requires `Pass.Read`. |\n| `POST /api/{tenantId}/passes` | Create a new pass for a customer. Requires `Pass.Write`. |\n| `PATCH /api/{tenantId}/passes` | Update one or more passes by internal ID or external identifiers (e.g. `id.crm.customerId=…`). Triggers a wallet refresh. |\n| `PATCH /api/{tenantId}/passes/{passId}` | Update a single pass by its internal ID. |\n| `PUT /api/{tenantId}/passes/{passId}/notification` | Send an Apple Wallet / Google Wallet push notification to a specific pass holder. |\n\nPasses are identified through **external identifiers** that link them to your source systems (CRM ID, loyalty number, ticket ID). Most update endpoints accept external identifiers so you never need to look up the internal `passId` first.\n\n> **Tip — force a data refresh**\n> Set `options.UpdateMetadata = true` in a PATCH body to force a full re-fetch from all configured connectors. Use `options.BypassQueue = true` for synchronous delivery instead of the default async queue.\n\n## Benefit\n\nA **benefit** is what a pass holds — a discount tier, a reward, a limited-use coupon, an entitlement. Benefits appear on the pass face and can carry a numeric value (points, balance, remaining uses) that changes over time through **movements**. A benefit is either created directly or granted from a **benefit template** configured in the back-office.\n\n| Operation | Description |\n|-----------|-------------|\n| `GET /api/{tenantId}/passes/{passId}/benefits` | List all benefits for a pass. |\n| `GET /api/{tenantId}/passes/{passId}/benefits/{benefitId}` | Retrieve a single benefit. |\n| `POST /api/{tenantId}/passes/{passId}/benefits` | Create a new benefit on a pass. |\n| `PUT /api/{tenantId}/passes/{passId}/benefits/{benefitId}` | Create or update (upsert) a benefit by its ID. |\n| `POST …/benefits/{benefitId}/movements` | Apply a movement (issuance, redemption, adjustment) to a benefit value. Returns a `movementId`. |\n| `DELETE …/benefits/{benefitId}` | Permanently delete a benefit. |\n\n## Privilege (deprecated)\n\nThe `PrivilegePass` tag is the previous name of the benefit API: the same operations under `/api/{tenantId}/passes/…/privileges`, with the request and response shapes they have always had. It is kept for existing integrations and forwards to the benefit API. New integrations use the `BenefitPass` endpoints above.\n\n## Scan\n\nThe `Scan` tag records barcode and QR code scan events. When a pass barcode is scanned — at a POS, a venue gate, or a redemption counter — call this endpoint to:\n\n- Correlate the raw scan value to the correct pass.\n- Record the scan with a timestamp and symbology type.\n- Emit a downstream event to connected systems (Bloomreach, CRM webhooks, etc.).\n\n| Field | Description |\n|-------|-------------|\n| `data` | The raw decoded barcode/QR value (3–2048 chars). Keep it stable — formatting changes break correlation. |\n| `type` | Symbology: `qrcode`, `pdf417`, `code128`, `ean13`, `datamatrix`, `nfc`, or `manual`. |\n\n> **Architecture note**: Call the Scan API from a backend relay rather than directly from scanning hardware. This keeps API keys server-side and allows retries, logging, and enrichment.\n\n## Authentication\n\nAll endpoints require an `X-API-KEY` header. API keys are tenant-scoped — a key issued for one tenant cannot access another tenant's data. Create and manage keys under **Settings → API Keys & Secrets** in the back-office.\n\n| Scope | Required for |\n|-------|-------------|\n| `Pass.Read` | Reading pass data |\n| `Pass.Write` | Creating, updating passes and benefits |\n| `PassScan.Scan` | Recording scan events |\n\n## Further reading\n\n- [Getting started with the API](https://docs.thewalletcrew.io/developers-guides/integration-guides/getting-started-with-the-api) — first API call walkthrough\n- [Manage pass lifecycle with the API](https://docs.thewalletcrew.io/developers-guides/integration-guides/wallet/pass-lifecycle) — create, update, notify, disable\n- [Benefit guide](https://docs.thewalletcrew.io/guides-animation/engage-and-animate/privilege-and-activation/privilege) — benefit types, sources, and movement tracking\n- [Scan API guide](https://docs.thewalletcrew.io/developers-guides/integration-guides/scan-api) — integration patterns and troubleshooting",
      "x-page-icon": "id-card",
      "x-page-title": "Pass Management",
      "x-page-description": "The core of The Wallet Crew API. These endpoints let you issue, read, update, and manage digital passes across Apple Wallet and Google Wallet — and record the real-world events that drive your loyalty, ticketing, and membership workflows."
    },
    {
      "name": "Pass",
      "x-parent": "Pass Management"
    },
    {
      "name": "Benefits",
      "x-parent": "Pass Management"
    },
    {
      "name": "Theme",
      "x-parent": "Pass Management"
    },
    {
      "name": "Scan",
      "x-parent": "Pass Management"
    },
    {
      "name": "StampCard",
      "x-parent": "Pass Management"
    },
    {
      "name": "PassExport",
      "x-parent": "Pass Management"
    },
    {
      "name": "Forms",
      "description": "The enrolment surface of The Wallet Crew. These endpoints power customer registration flows, store-aware redirects, and the store reference data that backs geolocation and attribution features.\n\n## Customer\n\nThe `Customer` tag exposes the enrolment form backend. An enrolment form is the web page customers use to join a programme and receive their wallet pass. It sits between your acquisition channel (QR code, email link, website CTA, mobile app) and the pass template.\n\nWhen a customer submits a form, The Wallet Crew:\n\n1. Creates or updates a **customer profile** (equivalent to a loyalty account).\n2. Validates consent and required fields.\n3. Issues the wallet pass with the correct \"Add to Wallet\" experience for Apple or Google.\n\n**Common use cases**\n\n- Retail loyalty enrolment via in-store QR code at checkout.\n- Post-purchase email link that opens a pre-filled form.\n- Mobile app deep link that resolves identity without asking questions again.\n- Clienteling tablet used by staff to enrol a customer on the spot.\n\n> **Data quality tip**: Collect only the identifiers you need. Short forms convert better and produce fewer placeholder entries. Returning customers can be identified early via social sign-in or email check-in — avoiding duplicate profiles.\n\n## Redirect\n\nThe `Redirect` tag manages short, tracked URLs and QR codes for enrolment journeys. A redirect wraps an enrolment form URL and injects parameters like `storeId`, language, or campaign source before forwarding the customer.\n\n| Operation | Description |\n|-----------|-------------|\n| List / create / update redirects | Manage the library of tracked entry points. |\n| Generate QR code | Produce a printable QR for a redirect URL. |\n| Track usage | Redirect events appear in the Insights database as `Redirect:Redirected`. |\n\nA single enrolment form can have many redirects — one per store, one per campaign, one per channel — without duplicating form configuration. Attribution data flows through the `storeId` and custom parameters you attach to each redirect.\n\n## Store\n\nThe `Store` tag manages the reference list of physical store locations. Store data is used in two places:\n\n- **Enrolment attribution**: when a redirect carries a `storeId`, the matching store record is attached to the customer profile.\n- **Geolocated notifications**: Apple Wallet and Google Wallet can surface a pass automatically when a customer is near a configured location.\n\n| Field | Description |\n|-------|-------------|\n| `name` | Display name shown on the pass or form. |\n| `address` | Full address for display purposes. |\n| `latitude` / `longitude` | Coordinates used for geolocation triggers. |\n| `externalId` | Your internal store identifier, used to correlate with POS or CRM data. |\n\n> Store data can be bulk-imported via flat file. See [Stores configuration guide](https://docs.thewalletcrew.io/configure/advanced-configuration/platform/data-and-integrations/stores).\n\n## Authentication\n\nAll endpoints require an `X-API-KEY` header scoped to the tenant.\n\n## Further reading\n\n- [Enrolment form guide](https://docs.thewalletcrew.io/guides-enrolment/enrolment/enrolment-form) — UX patterns, data quality, GDPR compliance\n- [Redirects guide](https://docs.thewalletcrew.io/guides-enrolment/enrolment/enrolment-form/redirect) — creating store-level QR codes\n- [Stores guide](https://docs.thewalletcrew.io/guides-enrolment/enrolment/enrolment-form/stores) — importing and managing location data\n- [Social sign-in](https://docs.thewalletcrew.io/guides-enrolment/enrolment/enrolment-form/social-sign-in) — Apple, Google, LINE, Facebook authentication",
      "x-page-icon": "wpforms",
      "x-page-title": "Forms",
      "x-page-description": "The enrolment surface of The Wallet Crew. These endpoints power customer registration flows, store-aware redirects, and the store reference data that backs geolocation and attribution features."
    },
    {
      "name": "Customer",
      "x-parent": "Forms"
    },
    {
      "name": "Redirect",
      "x-parent": "Forms"
    },
    {
      "name": "Store",
      "x-parent": "Forms"
    },
    {
      "name": "Tenant config",
      "description": "Everything needed to configure and operate a tenant. A **tenant** is an isolated workspace on The Wallet Crew platform — typically one brand, one region, or one programme. These endpoints manage the devices, scheduled tasks, secrets, API credentials, tenant settings, and webhook subscriptions that define how a tenant behaves.\n\n## Devices\n\nDevices are the scanners and terminals authorised to connect to **Pass Scanner** — the companion app used by staff to validate passes in real time.\n\n| Operation | Description |\n|-----------|-------------|\n| `GET /api/{tenantId}/devices` | List registered devices. Requires `Device.Read`. |\n| `POST /api/{tenantId}/devices` | Register a new device. |\n| `PUT /api/{tenantId}/devices/{deviceId}` | Update device name or settings. |\n| `DELETE /api/{tenantId}/devices/{deviceId}` | Remove a device and revoke its API key. |\n| `POST …/devices/{deviceId}/connect` | Connect a device: returns its API key and environment URI. |\n| `POST …/devices/{deviceId}/connections/reset` | Rotate the API key for a device. |\n\n> See [Manage devices guide](https://docs.thewalletcrew.io/guides-scan/scan/pass-scanner/manage-devices) for the full setup flow including QR code distribution.\n\n## Automations\n\nAn automation is a scheduled background task — data sync, pass updates, report exports, and more — running on a configurable cadence.\n\n| Operation | Description |\n|-----------|-------------|\n| `GET /api/{tenantId}/admin/automations` | List every configured automation. Requires `ConfigurationAutomation.Read`. |\n| `GET /api/{tenantId}/admin/automations/{automationId}` | Retrieve a single automation. |\n| `POST /api/{tenantId}/admin/automations` | Create an automation. Requires `ConfigurationAutomation.Write`. |\n| `PUT /api/{tenantId}/admin/automations/{automationId}` | Replace an automation in full; the id is immutable. |\n| `DELETE /api/{tenantId}/admin/automations/{automationId}` | Delete an automation; its execution history stays queryable. |\n| `GET /api/{tenantId}/admin/automations/executions` | List recent executions across all automations. Requires `ConfigurationAutomation.Read`. |\n| `GET /api/{tenantId}/admin/automations/{taskId}/executions` | Execution history for a specific automation. |\n| `GET /api/{tenantId}/admin/automations/{taskId}/executions/{executionId}` | Full detail and logs for a single execution. |\n| `POST /api/{tenantId}/admin/automations/{taskId}/reset` | Reset an automation's internal state. Requires `ConfigurationAutomation.Write`. |\n\n## Sftp\n\nRead-only visibility into the SFTP (Triglav) flat-file import feature. Customers drop\nCSV files via SFTP to bulk-update passes; these endpoints report whether the feature is\nenabled for the tenant, list the files in its inbox, and return the full import story\nfor one file — including which specific passes were touched and which failed.\n\n| Operation | Description |\n|-----------|-------------|\n| `GET /api/{tenantId}/admin/sftp/status` | Whether SFTP is enabled, plus a quick activity summary. |\n| `GET /api/{tenantId}/admin/sftp/files` | List inbox files, each tagged `pending`, `processed`, or `error`. |\n| `GET /api/{tenantId}/admin/sftp/files/{fileName}/log` | Full import log for one file, including per-pass outcomes. |\n\n> A tenant with no SFTP inbox simply has the feature disabled — every endpoint reports\n> this as `sftpEnabled: false` / an empty list, never a 404.\n\n## Secret\n\nSecrets are tenant-scoped key/value pairs used to store integration credentials (API tokens, signing keys, passwords) that connector scripts and configuration can reference without embedding secrets in plain text.\n\n| Operation | Description |\n|-----------|-------------|\n| `GET /api/{tenantId}/secrets` | List all secret keys (values are not returned). Requires `Secret.Read`. |\n| `GET /api/{tenantId}/secrets/{key}` | Retrieve a secret value by key. |\n| `PUT /api/{tenantId}/secrets/{key}` | Create or update a secret. |\n| `DELETE /api/{tenantId}/secrets/{key}` | Delete a secret. |\n\n## Security\n\nThe `Security` tag manages **API keys** — the credentials used to authenticate calls to the tenant API.\n\n| Operation | Description |\n|-----------|-------------|\n| `GET /api/{tenantId}/admin/apiKeys` | List all API keys for the tenant. |\n| `POST /api/{tenantId}/admin/apiKeys` | Create a new key. The plaintext token is returned **once** at creation. |\n| `PUT /api/{tenantId}/admin/apiKeys/{keyName}` | Update key metadata (name, scopes, expiry). |\n| `DELETE /api/{tenantId}/admin/apiKeys/{keyName}` | Revoke and delete a key. |\n\n> Each API key carries a set of permission scopes. A key without the required scope returns `403`. Use the principle of least benefit — give integrations only the scopes they need.\n\n## Tenant\n\nTenant endpoints manage the configuration files that define how a tenant is set up — templates, layout overrides, branding, connector settings.\n\n| Operation | Description |\n|-----------|-------------|\n| `GET /api/tenants` | List all tenants (Global Administrator only). |\n| `GET /api/tenants/{tenantId}` | Download the full tenant configuration as a ZIP archive. |\n| `PUT /api/tenants/{tenantId}` | Create or replace tenant configuration files. |\n| `PATCH /api/tenants/{tenantId}` | Partially update specific configuration files. |\n| `DELETE /api/tenants/{tenantId}` | Delete tenant configuration (Global Administrator only). |\n| `GET /api/tenants/{tenantId}/config/history` | View the configuration change history. |\n| `GET /api/tenants/{tenantId}/test` | Validate the tenant configuration without publishing. |\n\n## TenantConfiguration\n\nHigher-level tenant settings — programme name, locale defaults, custom domain, and platform-wide toggles.\n\n## WebHook\n\nWebhooks deliver real-time HTTP notifications to your endpoint whenever events occur in The Wallet Crew — pass installed, pass updated, scan recorded, customer created, and more.\n\n| Operation | Description |\n|-----------|-------------|\n| `POST /api/{tenantId}/webhooks` | Create a webhook subscription. Returns the `id` and a `signatureSecret`. |\n| `GET /api/{tenantId}/webhooks` | List subscriptions. |\n| `PATCH /api/{tenantId}/webhooks/{id}` | Update a subscription (URL, events, active state). |\n| `DELETE /api/{tenantId}/webhooks/{id}` | Remove a subscription. |\n\n**Verifying delivery**: Every webhook request includes these headers:\n\n| Header | Content |\n|--------|---------|\n| `x-neostore-signature` | HMAC-SHA256 over the raw request body, using the `signatureSecret`. |\n| `x-neostore-eventname` | The event type that triggered the delivery. |\n| `x-neostore-tenantid` | The tenant that emitted the event. |\n\n## Further reading\n\n- [API Keys & Secrets guide](https://docs.thewalletcrew.io/configure/advanced-configuration/platform/api-keys-and-secrets)\n- [Webhooks guide](https://docs.thewalletcrew.io/developers-guides/integration-guides/webhooks)\n- [Webhooks configuration](https://docs.thewalletcrew.io/developers-guides/integration-guides/webhooks/webhooks-configure)\n- [Manage devices guide](https://docs.thewalletcrew.io/guides-scan/scan/pass-scanner/manage-devices)",
      "x-page-icon": "sliders-h",
      "x-page-title": "Tenant Configuration",
      "x-page-description": "Everything needed to configure and operate a tenant. A **tenant** is an isolated workspace on The Wallet Crew platform — typically one brand, one region, or one programme. These endpoints manage the devices, scheduled tasks, secrets, API credentials, tenant settings, and webhook subscriptions that define how a tenant behaves."
    },
    {
      "name": "Automations",
      "x-parent": "Tenant config"
    },
    {
      "name": "BenefitTemplates",
      "x-parent": "Tenant config"
    },
    {
      "name": "Devices",
      "x-parent": "Tenant config"
    },
    {
      "name": "DeviceTelemetry",
      "x-parent": "Tenant config"
    },
    {
      "name": "Secret",
      "x-parent": "Tenant config"
    },
    {
      "name": "Security",
      "x-parent": "Tenant config"
    },
    {
      "name": "Sftp",
      "x-parent": "Tenant config"
    },
    {
      "name": "Tenant",
      "x-parent": "Tenant config"
    },
    {
      "name": "TenantConfiguration",
      "x-parent": "Tenant config"
    },
    {
      "name": "WebHook",
      "x-parent": "Tenant config"
    },
    {
      "name": "Tools",
      "description": "Utility endpoints that support common operational tasks: generating barcodes, managing the tenant cache, verifying email addresses, and querying the analytics database with KQL.\n\n## Barcode\n\nGenerate barcode and QR code images server-side. Useful when you need to embed a scannable code in a PDF, email, receipt, or printed document — without relying on the client to render it.\n\nSupported symbologies include QR Code, Code 128, PDF417, EAN-13, and Data Matrix. The response is an image in the requested format (PNG, SVG, or base64).\n\n## Cache\n\nThe Wallet Crew caches rendered pass content to reduce latency at scale. The `Cache` endpoints let you invalidate cached content for a tenant or a specific pass when data changes outside the normal update flow.\n\n| Operation | Description |\n|-----------|-------------|\n| Flush tenant cache | Force re-render of all passes on next request. |\n| Flush pass cache | Force re-render of a specific pass. |\n\n> Use cache flush sparingly. Normal pass updates via the Pass API already invalidate the relevant cache entries automatically.\n\n## EmailVerifier\n\nValidate an email address in real time — before creating a customer profile or issuing a pass. The verifier checks:\n\n- Syntax validity (RFC 5321).\n- Domain existence and MX record resolution.\n- Optionally, mailbox-level verification against the mail server.\n\nThis helps prevent duplicate or invalid profiles caused by typos at enrolment time.\n\n## Insights\n\nThe `Insights` endpoint runs **Kusto Query Language (KQL)** queries against the tenant's analytics database. This is the programmatic access point for custom dashboards, BI pipelines, scheduled reports, and data exports.\n\n### Database tables\n\n| Table | Retention | Description |\n|-------|-----------|-------------|\n| `Events` | Indefinite | Page views, API requests, pass lifecycle events, scan events, customer events. |\n| `Metrics` | Indefinite | Hourly snapshots of system state (active passes, install counts, etc.). |\n| `Logs` | 45 days | Platform traces and error logs for debugging. |\n\n### Common queries\n\n```kql\n// New customers over the last 30 days\nEvents\n| where eventType == \"Customer:Upserted\" and timestamp > ago(30d)\n| summarize NewCustomers = count() by bin(timestamp, 1d)\n```\n\n```kql\n// Pass installation trend\nEvents\n| where eventType == \"Pass:Installed\"\n| summarize Installations = count() by bin(timestamp, 1d)\n| order by timestamp asc\n```\n\n```kql\n// Redirect performance by day\nEvents\n| where eventType == \"Redirect:Redirected\"\n| summarize Redirects = count() by bin(timestamp, 1d)\n```\n\n### Key event types\n\n| Category | Event types |\n|----------|-------------|\n| Pass lifecycle | `Pass:Created`, `Pass:Updated`, `Pass:Installed`, `Pass:Uninstalled` |\n| Customer | `Customer:Upserted` |\n| Wallet actions | `action:addToAppleWallet`, `action:addToGoogleWallet` |\n| Social sign-in | `action:loginWithGoogle`, `action:loginWithApple` |\n| Tracking | `Request`, `PageView`, `Redirect:Redirected` |\n\n### Authentication and limits\n\n| Requirement | Value |\n|-------------|-------|\n| Scope | `Insights.Read` |\n| Rate limit | 60 requests / minute |\n| Query access | Single-tenant only — you cannot query another tenant's data |\n\n## Further reading\n\n- [Insights API guide](https://docs.thewalletcrew.io/developers-guides/integration-guides/insights-api) — KQL reference, tables, common queries, troubleshooting\n- [Analytics dashboards guide](https://docs.thewalletcrew.io/guides-monitoring/monitor/analytics-dashboards)\n- [KPI definitions](https://docs.thewalletcrew.io/guides-monitoring/monitor/kpi-definitions)",
      "x-page-icon": "tools",
      "x-page-title": "Tools",
      "x-page-description": "Utility endpoints that support common operational tasks: generating barcodes, managing the tenant cache, verifying email addresses, and querying the analytics database with KQL."
    },
    {
      "name": "Barcode",
      "x-parent": "Tools"
    },
    {
      "name": "Cache",
      "x-parent": "Tools"
    },
    {
      "name": "EmailVerifier",
      "x-parent": "Tools"
    },
    {
      "name": "Insights",
      "x-parent": "Tools"
    },
    {
      "name": "Internal",
      "description": "Internal platform endpoints used by The Wallet Crew infrastructure, the back-office, and the enrolment front-end. These are **not intended for external integrations**. They are documented here for transparency and for teams building white-label or embedded experiences on top of the platform.\n\n## Admin\n\nBack-office management endpoints. Used by the admin console to manage users, roles, permissions, and platform-level settings. Require elevated scopes (typically Global Administrator or Tenant Administrator).\n\n## CachedContent\n\nServes pre-rendered pass content (Apple `.pkpass` bundles, Google Wallet JWT payloads, download pages) from the platform cache. These endpoints are called by the Cinto SDK and by hosted download pages — not by API integrations.\n\n> Caching is transparent to API callers. Pass updates through the standard Pass API automatically invalidate the relevant cached entries.\n\n## Public\n\nUnauthenticated or lightly authenticated endpoints that serve public-facing content: enrolment form assets, hosted download pages, and the `/.well-known` device-registration endpoints required by Apple Wallet for push notification delivery.\n\n## Receipt\n\nGenerates and serves digital receipts linked to a pass. Used in post-transaction flows where a receipt should be displayed or delivered alongside a wallet pass update.\n\n## Warmup\n\nPlatform health and warmup probes. Called by infrastructure on startup and by load balancers to verify that the service is ready to handle traffic. Returns a simple `200 OK` when healthy.\n\n## A note on scope\n\nEndpoints in this group require internal scopes that are not available to tenant API keys. If you are building an integration that seems to require access to one of these endpoints, there is usually a public API equivalent — check the **Pass Management**, **Forms**, or **Tools** groups first.\n\n## Further reading\n\n- [Platform infrastructure overview](https://docs.thewalletcrew.io/developers-guides/pass-architecture/infrastructure)\n- [Pass data and sync](https://docs.thewalletcrew.io/developers-guides/pass-architecture/pass-data-and-sync)\n- [Security overview](https://docs.thewalletcrew.io/policies/privacy-and-security)",
      "x-page-icon": "lock",
      "x-page-title": "Internal",
      "x-page-description": "Internal platform endpoints used by The Wallet Crew infrastructure, the back-office, and the enrolment front-end. These are **not intended for external integrations**. They are documented here for transparency and for teams building white-label or embedded experiences on top of the platform."
    },
    {
      "name": "CachedContent",
      "x-parent": "Internal"
    },
    {
      "name": "Public",
      "x-parent": "Internal"
    },
    {
      "name": "Receipt",
      "x-parent": "Internal"
    },
    {
      "name": "Warmup",
      "x-parent": "Internal"
    },
    {
      "name": "Extensions",
      "description": "Connector-specific endpoints that bridge The Wallet Crew with third-party platforms. Each extension exposes the webhook receivers, sync operations, and data-push endpoints that a specific integration needs. Extensions are enabled per-tenant and scoped to the connector they serve.\n\n## Marketing automation\n\n### Actito\nReceives pass creation and update triggers from Actito scenarios. Enables wallet pass issuance and push notifications to be orchestrated directly from Actito journeys.\n[Actito connector guide](https://docs.thewalletcrew.io/connectors/marketing-automation/actito)\n\n### Klaviyo\nAccepts Klaviyo flow actions to create passes, trigger updates, and send push notifications. Events flow back to Klaviyo as profile properties and metric events for segmentation.\n[Klaviyo connector guide](https://docs.thewalletcrew.io/connectors/marketing-automation/klaviyo)\n\n### SFMC (Salesforce Marketing Cloud)\nExposes Journey Builder activity endpoints for pass updates and notifications. Also provides AMPscript helpers for generating authenticated pass links in Email Studio.\n[SFMC connector guide](https://docs.thewalletcrew.io/connectors/marketing-automation/salesforce-marketing-cloud)\n\n## Loyalty and CRM\n\n### Cegid\nIntegrates with **Cegid Retail Y2** and **Cegid UR** POS systems. Receives customer and transaction webhooks from Cegid to keep wallet passes in sync with loyalty balances and member data.\n[Cegid connector guide](https://docs.thewalletcrew.io/connectors/pos/cegid)\n\n### Comarch\nConnects Comarch loyalty programs to Apple Wallet and Google Wallet. Processes Kafka events and REST hooks from Comarch to update pass data in real time.\n[Comarch connector guide](https://docs.thewalletcrew.io/connectors/crm-and-fidelity/comarch)\n\n## Ticketing\n\n### Secutix\nDistributes event tickets issued by Secutix as wallet passes. Handles ticket creation, updates, and invalidation through Secutix webhook notifications.\n[Secutix connector guide](https://docs.thewalletcrew.io/connectors/ticketing/secutix)\n\n### Aparte\nConnects the Aparté (now Tick&Live) ticketing platform to wallet pass delivery. Manages ticket-to-pass mapping, lifecycle updates, and multi-template routing.\n[Aparté connector guide](https://docs.thewalletcrew.io/connectors/ticketing/aparte)\n\n### Yurplan\nDelivers Yurplan event tickets as wallet passes, with automatic sync from the Yurplan confirmation flow.\n[Yurplan connector guide](https://docs.thewalletcrew.io/connectors/ticketing/yurplan)\n\n## Wallet platform\n\n### ApplePass\nApple Wallet device registration and push notification delivery endpoints. Called directly by Apple devices during pass installation, update checks, and uninstallation — these are part of the [Apple PassKit Web Service](https://developer.apple.com/documentation/walletpasses/adding_a_web_service_to_update_passes) protocol and must not be called by your integration.\n\n### GooglePass\nGoogle Wallet JWT issuance and class management endpoints. Called during pass distribution and update flows for Google Wallet.\n\n## Security\n\n### Turnstile (Cloudflare)\nValidates Cloudflare Turnstile tokens on enrolment form submissions to block automated bots. The token is sent by the form client and verified server-side before the customer record is created.\n[Turnstile guide](https://docs.thewalletcrew.io/guides-enrolment/enrolment/enrolment-form/validation-rules/cloudflare-turnstile)\n\n## Authentication\n\nExtension endpoints use the same `X-API-KEY` authentication as the rest of the API, but the required scopes are connector-specific. Webhook receiver endpoints may additionally validate an HMAC signature or a shared secret from the originating platform.\n\n## Further reading\n\n- [Connectors overview](https://docs.thewalletcrew.io/connectors/wallet-pass-connectors)\n- [Custom connectors guide](https://docs.thewalletcrew.io/developers-guides/integration-guides/custom-connectors)\n- [Marketing automation connectors](https://docs.thewalletcrew.io/connectors/marketing-automation)\n- [POS connectors](https://docs.thewalletcrew.io/connectors/pos)\n- [Ticketing connectors](https://docs.thewalletcrew.io/connectors/ticketing)",
      "x-page-icon": "puzzle-piece",
      "x-page-title": "Extensions",
      "x-page-description": "Connector-specific endpoints that bridge The Wallet Crew with third-party platforms. Each extension exposes the webhook receivers, sync operations, and data-push endpoints that a specific integration needs. Extensions are enabled per-tenant and scoped to the connector they serve."
    },
    {
      "name": "Actito",
      "x-parent": "Extensions"
    },
    {
      "name": "Aparte",
      "x-parent": "Extensions"
    },
    {
      "name": "ApplePass",
      "x-parent": "Extensions"
    },
    {
      "name": "Cegid",
      "x-parent": "Extensions"
    },
    {
      "name": "Comarch",
      "x-parent": "Extensions"
    },
    {
      "name": "GooglePass",
      "x-parent": "Extensions"
    },
    {
      "name": "Klaviyo",
      "x-parent": "Extensions"
    },
    {
      "name": "Secutix",
      "x-parent": "Extensions"
    },
    {
      "name": "SFMC",
      "x-parent": "Extensions"
    },
    {
      "name": "Turnstile",
      "x-parent": "Extensions"
    },
    {
      "name": "Yurplan",
      "x-parent": "Extensions"
    },
    {
      "name": "Advanced",
      "description": "Additional API endpoints that do not belong to a specific functional group. These cover platform-level administration, data export, template management, access control, and observability.\n\n## Pass Export\n\nBulk-export pass data for a tenant. Returns pass records with identifiers, metadata, and current field values in a structured format suitable for CRM sync, BI pipelines, or migration.\n\n> For large exports, prefer paginated calls or the SFTP flat-file export. See [Import and export guide](https://docs.thewalletcrew.io/configure/advanced-configuration/wallet/import-and-export).\n\n## Templates\n\nProgrammatic access to pass template definitions — the visual and data configuration that controls how a pass looks in Apple Wallet and Google Wallet.\n\n| Operation | Description |\n|-----------|-------------|\n| List templates | Enumerate all templates configured for the tenant. |\n| Get template | Retrieve the full template definition including field layout and branding. |\n\n## API Keys\n\nA secondary API key management surface (the primary one is under **Tenant Configuration → Security**). Use these endpoints when managing keys as part of a provisioning pipeline.\n\n## Config\n\nRead or update runtime configuration values for the tenant. Overlaps with `Tenant` endpoints but focuses on in-memory configuration rather than file-based configuration archives.\n\n## Permissions, Roles, and Users\n\nBack-office identity management for the tenant:\n\n| Tag | Description |\n|-----|-------------|\n| `Permissions` | List and inspect permission scopes available on the platform. |\n| `Roles` | Create and manage role definitions that group permissions. |\n| `Users` | Manage back-office user accounts, role assignments, and invitations. |\n\n> See [User access guide](https://docs.thewalletcrew.io/configure/advanced-configuration/platform/user-access) for the full setup flow.\n\n## Google Classes Admin\n\nManage Google Wallet class definitions at the platform level. Google Wallet passes are built on top of a **class** (template) and an **object** (instance). These endpoints let you inspect and update class configurations when the standard template management UI is not sufficient.\n\n## Logs\n\nQuery raw platform logs for the tenant. Useful for troubleshooting integration failures, diagnosing connector errors, and auditing configuration changes.\n\n> For analytics queries (KQL), use the **Insights** endpoint under the **Tools** group instead.\n\n## Global\n\nCross-tenant utility endpoints available to Global Administrators. Includes platform health checks, tenant directory access, and infrastructure diagnostics.\n\n## Further reading\n\n- [Pass architecture](https://docs.thewalletcrew.io/developers-guides/pass-architecture)\n- [Import and export](https://docs.thewalletcrew.io/configure/advanced-configuration/wallet/import-and-export)\n- [User access configuration](https://docs.thewalletcrew.io/configure/advanced-configuration/platform/user-access)\n- [Apple Wallet template configuration](https://docs.thewalletcrew.io/configure/advanced-configuration/wallet/template-configuration)\n- [Google Wallet account setup](https://docs.thewalletcrew.io/configure/advanced-configuration/wallet/apple-and-google-wallet/google-wallet-account)",
      "x-page-icon": "code",
      "x-page-title": "Advanced",
      "x-page-description": "Additional API endpoints that do not belong to a specific functional group. These cover platform-level administration, data export, template management, access control, and observability."
    },
    {
      "name": "DeviceProfiles",
      "x-parent": "Advanced"
    },
    {
      "name": "DeviceSessions",
      "x-parent": "Advanced"
    },
    {
      "name": "Benefit",
      "x-parent": "Advanced"
    },
    {
      "name": "Templates",
      "x-parent": "Advanced"
    },
    {
      "name": "ApiKeys",
      "x-parent": "Advanced"
    },
    {
      "name": "Config",
      "x-parent": "Advanced"
    },
    {
      "name": "ConfigSchemas",
      "x-parent": "Advanced"
    },
    {
      "name": "ScriptTypings",
      "x-parent": "Advanced"
    },
    {
      "name": "CustomDomain",
      "x-parent": "Advanced"
    },
    {
      "name": "DownloadPages",
      "x-parent": "Advanced"
    },
    {
      "name": "EmailProvider",
      "x-parent": "Advanced"
    },
    {
      "name": "EmailTemplates",
      "x-parent": "Advanced"
    },
    {
      "name": "EnrolmentForms",
      "x-parent": "Advanced"
    },
    {
      "name": "EnrolmentLocales",
      "x-parent": "Advanced"
    },
    {
      "name": "ActitoScripts",
      "x-parent": "Advanced"
    },
    {
      "name": "AparteScripts",
      "x-parent": "Advanced"
    },
    {
      "name": "Bloomreach",
      "x-parent": "Advanced"
    },
    {
      "name": "BloomreachScripts",
      "x-parent": "Advanced"
    },
    {
      "name": "CegidY2",
      "x-parent": "Advanced"
    },
    {
      "name": "CegidY2Scripts",
      "x-parent": "Advanced"
    },
    {
      "name": "ComarchScripts",
      "x-parent": "Advanced"
    },
    {
      "name": "KlaviyoScripts",
      "x-parent": "Advanced"
    },
    {
      "name": "MarketingCloud",
      "x-parent": "Advanced"
    },
    {
      "name": "SecutixScripts",
      "x-parent": "Advanced"
    },
    {
      "name": "Shopify",
      "x-parent": "Advanced"
    },
    {
      "name": "ShopifyScripts",
      "x-parent": "Advanced"
    },
    {
      "name": "Flows",
      "x-parent": "Advanced"
    },
    {
      "name": "Media",
      "x-parent": "Advanced"
    },
    {
      "name": "PassTypes",
      "x-parent": "Advanced"
    },
    {
      "name": "PassTypeImages",
      "x-parent": "Advanced"
    },
    {
      "name": "Permissions",
      "x-parent": "Advanced"
    },
    {
      "name": "Roles",
      "x-parent": "Advanced"
    },
    {
      "name": "AppleSignIn",
      "x-parent": "Advanced"
    },
    {
      "name": "FacebookSignIn",
      "x-parent": "Advanced"
    },
    {
      "name": "GoogleSignIn",
      "x-parent": "Advanced"
    },
    {
      "name": "LineSignIn",
      "x-parent": "Advanced"
    },
    {
      "name": "Stores",
      "x-parent": "Advanced"
    },
    {
      "name": "Users",
      "x-parent": "Advanced"
    },
    {
      "name": "GoogleClassesAdmin",
      "x-parent": "Advanced"
    },
    {
      "name": "AppleWalletProvider",
      "x-parent": "Advanced"
    },
    {
      "name": "GoogleWalletProvider",
      "x-parent": "Advanced"
    },
    {
      "name": "Logs",
      "x-parent": "Advanced"
    },
    {
      "name": "Global",
      "x-parent": "Advanced"
    },
    {
      "name": "Invitations",
      "x-parent": "Advanced"
    },
    {
      "name": "Me",
      "x-parent": "Advanced"
    }
  ],
  "x-tagGroups": [{"name":"Pass Management","tags":["Pass","BenefitPass","Benefits","PrivilegePass","Theme","Scan","StampCard","PassExport"]},{"name":"Forms","tags":["Customer","Redirect","Store"]},{"name":"Tenant config","tags":["Automations","BenefitTemplates","Devices","DeviceTelemetry","Secret","Security","Sftp","Tenant","TenantConfiguration","WebHook"]},{"name":"Tools","tags":["Barcode","Cache","EmailVerifier","Insights"]},{"name":"Internal","tags":["Admin","CachedContent","Public","Receipt","Warmup"]},{"name":"Extensions","tags":["Actito","Aparte","ApplePass","Cegid","Comarch","GooglePass","Klaviyo","Secutix","SFMC","Turnstile","Yurplan"]},{"name":"Advanced","tags":["DeviceProfiles","DeviceSessions","Benefit","Templates","ApiKeys","Config","ConfigSchemas","ScriptTypings","CustomDomain","DownloadPages","EmailProvider","EmailTemplates","EnrolmentForms","EnrolmentLocales","ActitoScripts","AparteScripts","Bloomreach","BloomreachScripts","CegidY2","CegidY2Scripts","ComarchScripts","KlaviyoScripts","MarketingCloud","SecutixScripts","Shopify","ShopifyScripts","Flows","Media","PassTypes","PassTypeImages","Permissions","Roles","AppleSignIn","FacebookSignIn","GoogleSignIn","LineSignIn","Stores","Users","GoogleClassesAdmin","AppleWalletProvider","GoogleWalletProvider","Logs","Global","Invitations","Me"]}]
}