openapi: 3.0.0
info:
  title: XFA API
  version: '1'
servers:
  - url: 'https://api.xfa.tech'
    description: Production stack API url
  - url: 'https://test-api.xfa.tech'
    description: Test stack API url
security:
  - bearerAuth: []
paths:
  '/organizations/{organizationId}/users/{email}/mfa':
    parameters:
      - in: path
        name: organizationId
        required: true
        schema:
          type: string
          minLength: 1
      - in: path
        name: email
        required: true
        schema:
          type: string
          minLength: 1
    get:
      operationId: getUserMfa
      summary: Read the user's MFA registrations
      responses:
        '200':
          description: Safe metadata; absent users have an empty overview.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/MfaSummary'
        '403':
          description: Not authorized for this organization
    delete:
      operationId: removeUserMfa
      summary: Remove selected MFA registrations for one user
      description: 'Administrator only, with the existing MFA gate. Requires a scoped revision from the overview. Preserves other methods and existing sessions. The silent method without deviceId and credentialId removes all silent MFA for this user only. The passkey method includes security keys; credentialId selects one registration, including a silent MFA registration without a device.'
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/MfaRemoval'
      responses:
        '204':
          description: Removed or already absent
        '400':
          description: Invalid selection
        '403':
          description: Not authorized
        '409':
          description: Registration changed; refresh and confirm again
  /pricing-plans:
    get:
      summary: List all global plan definitions
      x-internal: true
      tags:
        - PricingPlans
      responses:
        '200':
          description: Returns all plan definitions
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/GlobalPlanDefinition'
  /pricing-plans/apply:
    post:
      summary: Apply plan definitions to matching organizations (async)
      description: 'Brings each matching organization up to the latest revision of its plan. Only the plan fields and feature flags the plan edits changed are updated, and only where the organization still had the old plan value; values set for an organization by hand are kept. Organizations already on the latest revision are not changed.'
      x-internal: true
      tags:
        - PricingPlans
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - includeCustomPlans
              properties:
                planName:
                  type: string
                  description: 'If set, apply only to organizations on this specific plan, whether standard or custom (takes precedence over includeCustomPlans). If omitted, apply to all standard plans.'
                  example: Advanced
                includeCustomPlans:
                  type: boolean
                  description: 'When planName is omitted, whether to also apply to organizations on custom (non-standard) plans. Ignored when planName is set.'
                  default: false
      responses:
        '202':
          description: Apply started — organizations will be updated asynchronously
          content:
            application/json:
              schema:
                type: object
                properties:
                  message:
                    type: string
                    example: apply started
  '/pricing-plans/{planName}':
    put:
      summary: Update a global plan definition
      description: 'Every change is stored by the billing service as a new plan revision with what changed and who changed it (the signed-in sys admin). Organizations only change when the plan is applied, and then only the fields the edits changed, where the organization still had the old plan value.'
      x-internal: true
      tags:
        - PricingPlans
      parameters:
        - in: path
          name: planName
          schema:
            type: string
          required: true
          description: The plan name (e.g. Advanced)
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/GlobalPlanDefinition'
      responses:
        '204':
          description: Plan definition updated
        '400':
          description: Invalid request body
        '409':
          description: The plan was changed by someone else; reload it and try again
  '/pricing-plans/{planName}/revisions':
    get:
      summary: List a plan's revisions
      description: 'Every change to the plan, newest first, with what changed and who changed it. Revision 1 is the plan as it was when revision tracking started.'
      x-internal: true
      tags:
        - PricingPlans
      parameters:
        - in: path
          name: planName
          schema:
            type: string
          required: true
          description: The plan name (e.g. Advanced)
      responses:
        '200':
          description: The plan's revisions
          content:
            application/json:
              schema:
                type: array
                items:
                  type: object
                  description: 'An immutable snapshot of a plan definition, with what the change did and who made it.'
                  properties:
                    planName:
                      type: string
                    revision:
                      type: integer
                    definition:
                      $ref: '#/components/schemas/GlobalPlanDefinition'
                    changes:
                      type: object
                      properties:
                        paymentPlan:
                          type: array
                          items:
                            type: object
                            properties:
                              field:
                                type: string
                                example: NrOfPolicies
                              from:
                                description: 'The field''s value before (number, boolean or frequency string)'
                              to:
                                description: 'The field''s value after (number, boolean or frequency string)'
                        flagsAdded:
                          type: array
                          items:
                            type: string
                        flagsRemoved:
                          type: array
                          items:
                            type: string
                        pricingChanged:
                          type: boolean
                    changedBy:
                      type: string
                      description: 'Email of the sys admin who made the change, or a system actor'
                    changedAt:
                      type: string
                      format: date-time
  /discount-codes:
    get:
      summary: List all discount codes
      x-internal: true
      tags:
        - DiscountCodes
      responses:
        '200':
          description: Returns all discount codes
          content:
            application/json:
              schema:
                type: array
                items:
                  type: object
                  properties:
                    OrganizationID:
                      type: string
                    Date:
                      type: string
                      description: The discount code string
                    Percentage:
                      type: number
                    DurationMonths:
                      type: integer
                    CodeType:
                      type: string
                      enum:
                        - one-time
                        - repeatable
                    Tag:
                      type: string
                      description: Free text reference for who received the code
                    Redeemed:
                      type: boolean
                    RedeemedBy:
                      type: string
                    RedeemedAt:
                      type: string
                    CreatedAt:
                      type: string
                  required:
                    - Date
                    - Percentage
                    - DurationMonths
                    - CodeType
    post:
      summary: Create discount codes
      x-internal: true
      tags:
        - DiscountCodes
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                percentage:
                  type: number
                duration_months:
                  type: integer
                code_type:
                  type: string
                  enum:
                    - one-time
                    - repeatable
                count:
                  type: integer
                tag:
                  type: string
                  description: Free text reference for who received the discount codes
              required:
                - percentage
                - duration_months
                - code_type
      responses:
        '201':
          description: Discount codes created
          content:
            application/json:
              schema:
                type: object
                properties:
                  codes:
                    type: array
                    items:
                      type: string
                required:
                  - codes
    delete:
      summary: Delete a discount code
      x-internal: true
      tags:
        - DiscountCodes
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/DeleteDiscountCodeRequest'
      responses:
        '200':
          description: Discount code deleted
  /discount-codes/redeem:
    post:
      summary: Redeem a discount code
      x-internal: true
      tags:
        - DiscountCodes
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                code:
                  type: string
                organization_id:
                  type: string
              required:
                - code
                - organization_id
      responses:
        '200':
          description: Discount code redeemed
          content:
            application/json:
              schema:
                type: object
                properties:
                  message:
                    type: string
  /affiliations:
    post:
      summary: Create an affiliation
      x-internal: true
      tags:
        - Affiliations
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/AffiliationRequestBody'
      responses:
        '200':
          description: Affiliation created
    get:
      summary: Get all affiliations
      x-internal: true
      tags:
        - Affiliations
      responses:
        '200':
          description: Returns all affiliations
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ListAffiliation'
    delete:
      summary: Delete an affiliation
      x-internal: true
      tags:
        - Affiliations
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                device_token:
                  type: string
                  description: Device token
                organization_id:
                  type: string
                  description: Organization ID
      responses:
        '204':
          description: Affiliation deleted
        '409':
          description: Device details changed during removal. Refresh and retry.
  /affiliations/affiliations-admin:
    delete:
      summary: Delete an affiliation by admin
      x-internal: true
      tags:
        - Affiliations
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                organization_id:
                  type: string
                  description: Organization ID
                device_ids:
                  type: array
                  items:
                    type: string
                  description: Device IDs
                email:
                  type: string
                  description: Email address of the user whose invitations should also be removed
      responses:
        '204':
          description: Affiliation deleted
        '409':
          description: The approvals of one or more devices changed during removal. Every other device was removed (including its shadow); only the listed devices remain and can be retried.
          content:
            application/json:
              schema:
                type: object
                properties:
                  error:
                    type: string
                  conflicting_device_ids:
                    type: array
                    items:
                      type: string
  /connect/trustcloud:
    post:
      summary: Connect to TrustCloud
      tags:
        - Connect
      x-internal: true
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                organizationId:
                  type: string
                  description: The ID of the organization to connect
                apiKey:
                  type: string
                  description: TrustCloud API key
              required:
                - organizationId
                - apiKey
      responses:
        '200':
          description: Successfully connected to TrustCloud
  /connect/drata:
    post:
      summary: Connect to Drata
      tags:
        - Connect
      x-internal: true
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                organizationId:
                  type: string
                  description: The ID of the organization to connect
                drataApiKey:
                  type: string
                  description: Drata API key
              required:
                - organizationId
                - drataApiKey
      responses:
        '200':
          description: Successfully connected to Drata
  /connect/thoropass:
    post:
      summary: Connect to Thoropass
      tags:
        - Connect
      x-internal: true
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                organizationId:
                  type: string
                  description: The ID of the organization to connect
                clientId:
                  type: string
                  description: Thoropass client ID
                clientSecret:
                  type: string
                  description: Thoropass client secret
              required:
                - organizationId
                - clientId
                - clientSecret
      responses:
        '200':
          description: Successfully connected to Thoropass
  /connect/vanta:
    post:
      summary: Connect to Vanta
      tags:
        - Connect
      x-internal: true
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                organization_id:
                  type: string
                  description: The ID of the organization to connect
                code:
                  type: string
                  description: Vanta OAuth authorization code
                redirect_uri:
                  type: string
                  description: Vanta OAuth redirect URI
              required:
                - organization_id
                - code
                - redirect_uri
      responses:
        '200':
          description: Successfully connected to Vanta
  /connect/noru:
    post:
      summary: Connect to Noru
      tags:
        - Connect
      x-internal: true
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                organizationId:
                  type: string
                  description: The ID of the organization to connect
                noruApiKey:
                  type: string
                  description: Noru API key
              required:
                - organizationId
                - noruApiKey
      responses:
        '200':
          description: Successfully connected to Noru
  /connect/mem:
    post:
      summary: Connect to Microsoft Endpoint Manager
      tags:
        - Connect
      x-internal: true
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                organization_id:
                  type: string
                  description: The ID of the organization to connect
                code:
                  type: string
                  description: OAuth authorization code from Microsoft
                redirect_uri:
                  type: string
                  description: Redirect URI used in the OAuth flow
              required:
                - organization_id
                - code
                - redirect_uri
      responses:
        '204':
          description: Successfully connected to Microsoft Endpoint Manager
  /connect/mem/settings:
    patch:
      summary: Update MEM settings
      tags:
        - Connect
      x-internal: true
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                organization_id:
                  type: string
                  description: The ID of the organization
                extension_attribute:
                  type: integer
                  description: Extension attribute number (1-15) used to store compliance status
                  minimum: 1
                  maximum: 15
              required:
                - organization_id
                - extension_attribute
      responses:
        '204':
          description: Successfully updated MEM settings
  '/connect/{organizationId}/list':
    get:
      summary: List connections for an organization
      tags:
        - Connect
      x-internal: true
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns the list of connections for the organization
          content:
            application/json:
              schema:
                type: object
                properties:
                  vanta:
                    type: boolean
                    description: Whether Vanta is connected
                  thoropass:
                    type: boolean
                    description: Whether Thoropass is connected
                  drata:
                    type: boolean
                    description: Whether Drata is connected
                  trustcloud:
                    type: boolean
                    description: Whether Trustcloud is connected
                  noru:
                    type: boolean
                    description: Whether Noru is connected
  '/organizations/{organizationId}/connections/{uuid}':
    delete:
      summary: Delete a connection
      tags:
        - Connect
      x-internal: true
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: uuid
          description: UUID of the connection to delete
          required: true
          schema:
            type: string
      responses:
        '204':
          description: Connection successfully deleted
        '403':
          description: Not authorized to delete this connection
        '404':
          description: Connection not found
  /messaging/connect:
    post:
      summary: Connect a messaging integration
      tags:
        - Messaging
      x-internal: true
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                organization_id:
                  type: string
                  description: The ID of the organization to connect
                type:
                  type: string
                  enum:
                    - slack
                    - teams
                  description: Messaging provider to connect
                code:
                  type: string
                  description: The OAuth authorization code from the messaging platform
                tenant_id:
                  type: string
                  description: Microsoft tenant ID for Teams
                state:
                  type: string
                  description: The OAuth state value returned by the Teams consent flow
                redirect_uri:
                  type: string
                  description: The redirect URI used during the OAuth authorization request
              required:
                - organization_id
                - type
      responses:
        '200':
          description: Successfully connected messaging integration
          content:
            application/json:
              schema:
                type: object
                properties:
                  connection_id:
                    type: string
                    description: The ID of the created connection
                  connection_status:
                    type: string
                    description: 'Provider-neutral connection status, such as connected or tentative'
        '400':
          description: Invalid request
        '403':
          description: Not authorized
  /messaging/teams/consent-url:
    post:
      summary: Create a Microsoft Teams admin consent URL
      tags:
        - Messaging
      x-internal: true
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                organization_id:
                  type: string
                  description: The ID of the organization requesting Teams consent
                redirect_uri:
                  type: string
                  description: The dashboard URI where Microsoft redirects after admin consent
              required:
                - organization_id
                - redirect_uri
      responses:
        '200':
          description: Returns Teams consent URL details
          content:
            application/json:
              schema:
                type: object
                properties:
                  state:
                    type: string
                  consent_url:
                    type: string
                  expires_at:
                    type: integer
                    format: int64
        '400':
          description: Invalid request
        '403':
          description: Not authorized
  /messaging/teams/disconnect-teardown/consent-url:
    post:
      summary: Create a Microsoft Teams disconnect teardown admin consent URL
      tags:
        - Messaging
      x-internal: true
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/TeamsDisconnectTeardownConsentURLRequest'
      responses:
        '200':
          description: Returns Teams disconnect teardown consent URL details
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/TeamsDisconnectTeardownConsentURLResponse'
        '400':
          description: Invalid request
        '403':
          description: MFA required or invalid
        '404':
          description: Connection not found
  /messaging/teams/disconnect-teardown/callback:
    post:
      summary: Complete a Microsoft Teams disconnect teardown callback
      tags:
        - Messaging
      x-internal: true
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/TeamsDisconnectTeardownCallbackRequest'
      responses:
        '200':
          description: Returns Teams disconnect teardown results
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/TeamsDisconnectTeardownCallbackResponse'
        '400':
          description: Invalid request
        '403':
          description: MFA required or invalid
        '404':
          description: Connection not found
  '/messaging/{connectionId}':
    delete:
      summary: Disconnect a messaging integration
      tags:
        - Messaging
      x-internal: true
      parameters:
        - in: path
          name: connectionId
          description: ID of the messaging connection to disconnect
          required: true
          schema:
            type: string
      responses:
        '204':
          description: Successfully disconnected messaging integration
        '403':
          description: Not authorized
        '404':
          description: Connection not found
  '/messaging/organization/{organizationId}':
    get:
      summary: List messaging connections for an organization
      tags:
        - Messaging
      x-internal: true
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns the list of messaging connections for the organization
          content:
            application/json:
              schema:
                type: array
                items:
                  type: object
                  properties:
                    connection_id:
                      type: string
                    organization_id:
                      type: string
                    type:
                      type: string
                    provider:
                      type: string
                    team_id:
                      type: string
                    team_name:
                      type: string
                    connection_status:
                      type: string
                    connected:
                      type: boolean
        '403':
          description: Not authorized
  /demo:
    post:
      summary: Request a demo
      description: Submit a demo request form that will be sent to the XFA team
      operationId: requestDemo
      x-internal: true
      tags:
        - Demo
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - email
              properties:
                firstname:
                  type: string
                  description: First name of the person requesting the demo
                  example: John
                lastname:
                  type: string
                  description: Last name of the person requesting the demo
                  example: Doe
                company:
                  type: string
                  description: Company name of the person requesting the demo
                  example: Acme Inc
                email:
                  type: string
                  description: Email address of the person requesting the demo. Gmail addresses are not accepted.
                  example: john.doe@acme.com
                description:
                  type: string
                  description: Additional information about the demo request
                  example: I would like to learn more about your product
      responses:
        '200':
          description: Demo request successfully submitted
          content:
            text/plain:
              schema:
                type: string
                example: /demo-requested
        '400':
          description: Bad request - Invalid email format or blacklisted email
          content:
            text/plain:
              schema:
                type: string
                example: Email is not valid
        '403':
          description: Forbidden - Wrong HTTP method
          content:
            text/plain:
              schema:
                type: string
                example: Wrong method
        '500':
          description: Internal server error - Invalid JSON or notification service error
          content:
            text/plain:
              schema:
                type: string
                example: json not valid
  /devices:
    get:
      summary: Return all devices
      tags:
        - Devices
      parameters:
        - in: query
          name: organization_id
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: query
          name: policyId
          description: policyId
          required: false
          schema:
            type: string
        - in: query
          name: add_cves
          description: add_cves
          required: false
          schema:
            type: string
        - in: query
          name: use_decisions
          description: Include evaluation decisions in the response
          required: false
          schema:
            type: string
      responses:
        '200':
          description: Returns all devices
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ListDevicesWithIdentityResponse'
  /devices/count:
    get:
      summary: Get the count of devices
      x-internal: true
      tags:
        - Devices
      parameters:
        - in: query
          name: organization_id
          description: ID of Organization
          required: false
          schema:
            type: string
        - in: query
          name: date
          description: Date
          required: false
          schema:
            type: string
        - in: query
          name: start_date_unix
          description: Start date
          required: false
          schema:
            type: string
        - in: query
          name: end_date_unix
          description: End date
          required: false
          schema:
            type: string
        - in: query
          name: only_shadows
          description: show only shadows
          required: false
          schema:
            type: string
      responses:
        '200':
          description: Returns the count of devices
          content:
            application/json:
              schema:
                type: object
                properties:
                  count:
                    type: integer
                    description: Count of devices
                  connect_count:
                    type: integer
                    description: Count of connected devices
  /devices/count-users:
    get:
      summary: Get the count of users
      x-internal: true
      tags:
        - Devices
      parameters:
        - in: query
          name: organization_id
          description: ID of Organization
          required: false
          schema:
            type: string
        - in: query
          name: date
          description: Date
          required: false
          schema:
            type: string
        - in: query
          name: start_date_unix
          description: Start date
          required: false
          schema:
            type: string
        - in: query
          name: end_date_unix
          description: End date
          required: false
          schema:
            type: string
        - in: query
          name: only_shadows
          description: Todo only connected devices?
          required: false
          schema:
            type: string
      responses:
        '200':
          description: Returns the count of users
          content:
            application/json:
              schema:
                type: object
                properties:
                  count:
                    type: integer
                    description: Count of users
                  connect_count:
                    type: integer
                    description: Count of connected users
  /devices/count-users/current:
    get:
      summary: Get the number of people in the People list now
      description: 'The users with a device that submitted in the last 30 days, one per email: the People list count and the lowest seat count a seat decrease accepts (XFA-3787). Not the billed month count of /devices/count-users.'
      x-internal: true
      tags:
        - Devices
      parameters:
        - in: query
          name: organization_id
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: The People list count
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/CurrentUserCountResponse'
        '400':
          description: Missing organization_id
        '403':
          description: Not authorized for the organization
        '500':
          description: The count could not be read
  /devices/grouped:
    get:
      summary: Return all devices grouped by organization
      x-internal: true
      tags:
        - Devices
      parameters:
        - in: query
          name: organization_id
          description: organizationId
          required: false
          schema:
            type: string
        - in: query
          name: exclusive_start_key
          description: exclusive_start_key
          required: false
          schema:
            type: string
        - in: query
          name: policyId
          description: policyId
          required: false
          schema:
            type: string
        - in: query
          name: add_cves
          description: add_cves
          required: false
          schema:
            type: string
        - in: query
          name: use_decisions
          description: Include evaluation decisions in the response
          required: false
          schema:
            type: string
        - in: query
          name: from_date
          description: Filter devices from this date (RFC3339 format)
          required: false
          schema:
            type: string
            format: date-time
            example: '2023-01-01T00:00:00Z'
        - in: query
          name: to_date
          description: Filter devices to this date (RFC3339 format)
          required: false
          schema:
            type: string
            format: date-time
            example: '2023-12-31T23:59:59Z'
      responses:
        '200':
          description: Returns all devices grouped by organization
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/GroupedDevice'
  /devices/grouped/trial:
    get:
      summary: Returns trial-limited devices grouped by user
      x-internal: true
      tags:
        - devices
      parameters:
        - in: query
          name: organization_id
          description: organizationId
          required: false
          schema:
            type: string
        - in: query
          name: policyId
          description: policyId
          required: false
          schema:
            type: string
        - in: query
          name: add_cves
          description: add_cves
          required: false
          schema:
            type: string
        - in: query
          name: use_decisions
          description: Include evaluation decisions in the response
          required: false
          schema:
            type: string
        - in: query
          name: from_date
          description: Only include devices submitted on or after this RFC3339 timestamp
          required: false
          schema:
            type: string
            format: date-time
        - in: query
          name: to_date
          description: Only include devices submitted on or before this RFC3339 timestamp
          required: false
          schema:
            type: string
            format: date-time
      responses:
        '200':
          description: 'Returns devices grouped by user up to the organization''s configured trial user limit, defaulting to 10, and prioritizing users with verified devices first'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/GroupedDevice'
  /devices/tags:
    get:
      summary: Get all tags for an organization
      x-internal: true
      tags:
        - Devices
      parameters:
        - in: query
          name: organization_id
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns list of tags for the organization
          content:
            application/json:
              schema:
                type: array
                items:
                  type: string
                description: List of tags
        '400':
          description: Bad Request - organization_id is required
        '403':
          description: Forbidden - User is not authorized to access this organization
        '500':
          description: Internal Server Error
  /invitations:
    post:
      summary: Create an invitation
      x-internal: true
      tags:
        - Invitations
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/InvitationRequest'
      responses:
        '200':
          description: Invitation created
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/InvitationResponse'
    put:
      summary: Resend invitation
      x-internal: true
      tags:
        - Invitations
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/ResendInvitationRequest'
      responses:
        '204':
          description: Invitation resent
  '/invitations/{invitationToken}':
    get:
      summary: Get invitation information
      x-internal: true
      tags:
        - Invitations
      parameters:
        - in: path
          name: invitationToken
          description: token linked to invitation
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns the invitation information
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/InvitationInformationResponse'
  /organizations:
    post:
      summary: Create a new organization
      tags:
        - Organizations
      x-internal: true
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/OrganizationsCreateRequestBody'
      responses:
        '200':
          description: Returns the organization
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/OrganizationsCreateResponse'
    get:
      summary: Return all organizations
      parameters:
        - name: start
          in: query
          description: The index of the first organization to return
          required: false
          schema:
            type: integer
        - name: limit
          in: query
          description: The maximum number of organizations to return
          required: false
          schema:
            type: integer
      tags:
        - Organizations
      responses:
        '200':
          description: Returns all organizations
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/OrganizationsListResponse'
  /organizations/validate-vat:
    post:
      summary: Validate a VAT number against the VIES database
      description: Validates a VAT number against the official European Union VIES (VAT Information Exchange System) database. Includes retry logic and rate limiting to comply with VIES best practices.
      tags:
        - Organizations
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                vat:
                  type: string
                  description: 'VAT number to validate (e.g., NL123456789B01)'
              required:
                - vat
      responses:
        '200':
          description: VAT validation result
          content:
            application/json:
              schema:
                type: object
                properties:
                  valid:
                    type: boolean
                    description: Whether the VAT number is valid according to VIES
                  country_code:
                    type: string
                    description: Country code extracted from VAT number
                  vat_number:
                    type: string
                    description: VAT number without country code
                  name:
                    type: string
                    description: Company name from VIES (if valid)
                  address:
                    type: string
                    description: Company address from VIES (if valid)
                  request_date:
                    type: string
                    format: date-time
                    description: Date of the validation request
                  request_identifier:
                    type: string
                    description: Request identifier for audit purposes
                required:
                  - valid
        '400':
          description: Bad request - invalid VAT number format
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '429':
          description: Too many requests - rate limit exceeded
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '500':
          description: Internal server error or VIES service unavailable
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '503':
          description: VIES service temporarily unavailable
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
  '/organizations/{organizationId}':
    get:
      summary: Request organization information
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns the organization
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/OrganizationResponse'
        '400':
          description: Bad request
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '403':
          description: Forbidden
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '404':
          description: Not found
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
      '/organizations/{organizationId}/pdf':
        get:
          tags:
            - Services API
          summary: Download PDF report for an organization
          description: 'Downloads a PDF report for an organization. If no month is specified, returns the latest available PDF. If a month is specified, returns the PDF for that specific month.'
          parameters:
            - in: path
              name: organizationId
              schema:
                type: string
              required: true
              description: ID of the organization
            - in: query
              name: month
              schema:
                type: string
              required: false
              description: 'Month in format YYYYMM. If not specified, returns the latest available PDF.'
          responses:
            '200':
              description: PDF file download
              content:
                application/pdf:
                  schema:
                    type: string
                    format: binary
              headers:
                Content-Disposition:
                  description: Filename for download
                  schema:
                    type: string
            '400':
              description: Bad request - invalid month format
            '404':
              description: PDF not found for the given organization and month
    put:
      summary: Update an organization
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/OrganizationsUpdateRequestBody'
      responses:
        '204':
          description: Organization updated
        '400':
          description: The organization is not valid; the body is the reason as plain text (for example "Name of the organization cannot contain a phone number").
        '409':
          description: 'The organization changed concurrently, or admin MFA approval is still enabled while its feature flag is being removed.'
    patch:
      summary: Patch an organization
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              description: Partial update for an organization
              properties:
                custom_message_onboarding:
                  type: string
                  nullable: true
                  description: Custom message shown to end users on the webflow onboarding screen
                custom_message_sign_in:
                  type: string
                  nullable: true
                  description: Custom message shown to end users on the webflow sign-in / enforcement screen
                self_invite_enabled:
                  type: boolean
                  nullable: true
                  description: Allow verified native app users to request self-invite when eligible
                exclude_from_customer_metrics:
                  type: boolean
                  nullable: true
                  description: Keeps this organization out of company-wide customer metrics. Only system administrators may change it. null clears it.
                manual_invite_send_slack:
                  type: boolean
                  description: Last-used Slack toggle state in the manual Invite users popup.
                manual_invite_send_teams:
                  type: boolean
                  description: Last-used Microsoft Teams toggle state in the manual Invite users popup.
                default_language:
                  $ref: '#/components/schemas/Language'
      responses:
        '204':
          description: Organization patched
        '400':
          description: The organization is not valid; the body is the reason as plain text (for example "Name of the organization cannot contain a phone number").
        '409':
          description: 'The organization changed concurrently, or admin MFA approval is still enabled while its feature flag is being removed.'
    delete:
      summary: Delete an organization
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '204':
          description: Organization deleted
  '/organizations/{organizationId}/hard-delete':
    delete:
      summary: Hard delete an organization
      description: Hard delete an organization
      operationId: hardDeleteOrganization
      x-internal: true
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
      responses:
        '204':
          description: Organization deleted
  '/organizations/{organizationId}/restore':
    post:
      summary: Restore a soft-deleted organization
      description: Restore a soft-deleted organization
      operationId: restoreOrganization
      x-internal: true
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
      responses:
        '204':
          description: Organization restored
  '/organizations/{organizationId}/applications':
    post:
      summary: Create a new application
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Application'
      responses:
        '200':
          description: Returns the application
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Application'
    get:
      summary: Request application information
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns the application
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ApplicationsList'
  '/organizations/{organizationId}/counters':
    get:
      summary: Request organization counters
      description: Daily sign-in verification counters for the organization.
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: query
          name: number_of_days
          description: 'Number of days to return, 1 to 400. Missing or invalid uses the service default (30).'
          required: false
          schema:
            type: integer
            minimum: 1
            maximum: 400
        - in: query
          name: nr_of_days
          description: 'Older name for number_of_days, used only when number_of_days is absent or invalid.'
          required: false
          deprecated: true
          schema:
            type: integer
      responses:
        '200':
          description: 'Returns the organization counters, one per day'
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/OrganizationCounters'
  '/organizations/{organizationId}/billing-settings':
    get:
      summary: Request billing settings
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns the billing settings
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Billing-Settings'
    post:
      summary: Update billing settings
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Billing-Settings'
      responses:
        '204':
          description: Billing settings updated
    put:
      summary: Add mid-cycle licenses
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/AddLicensesRequest'
      responses:
        '200':
          description: Licenses added
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/AddLicensesResponse'
        '400':
          description: Invalid quantity or idempotency key
        '403':
          description: Caller is not authorized or organization billing access is blocked
        '409':
          description: 'Idempotency conflict, unsupported contract pricing, or organization license limit reached'
        '500':
          description: Billing service request failed
    patch:
      summary: Increment awareness quota
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Awareness quota updated
          content:
            application/json:
              schema:
                type: object
                properties:
                  used:
                    type: integer
                  limit:
                    type: integer
                  remaining:
                    type: integer
        '429':
          description: Quota limit exceeded
          content:
            application/json:
              schema:
                type: object
                properties:
                  error:
                    type: string
                  used:
                    type: integer
                  limit:
                    type: integer
  '/organizations/{organizationId}/plan-options':
    get:
      summary: Request self-service plan options
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns available plans and current billing context
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PlanOptionsResponse'
  '/organizations/{organizationId}/plan-change/preview':
    post:
      summary: Preview a self-service plan change
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/PlanChangeRequest'
      responses:
        '200':
          description: Returns the plan change preview
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PlanChangeResponse'
        '400':
          description: Invalid request payload
  '/organizations/{organizationId}/plan-change/confirm':
    post:
      summary: Confirm a self-service plan change
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/PlanChangeRequest'
      responses:
        '200':
          description: Plan change accepted
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PlanChangeResponse'
        '400':
          description: 'Invalid or blocked plan change, or a checkout billing refused (see error_code)'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PlanChangeResponse'
  '/organizations/{organizationId}/plan-change/cancel':
    post:
      summary: Cancel a scheduled plan change
      description: 'Withdraws a plan change scheduled for the next renewal date before it is applied, so the organization stays on its current plan. A change waiting for a checkout is not canceled here; the payment webhook clears it when the payment fails or is canceled.'
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: 'The canceled change, with status canceled'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PlanChangeResponse'
        '404':
          description: No pending plan change
        '409':
          description: The pending plan change is waiting for checkout
  '/organizations/{organizationId}/seat-change/preview':
    post:
      summary: Preview a seat decrease at the next renewal
      description: 'Read-only evaluation of a self-service seat decrease (XFA-3787). target_seats is the seat total the admin wants from the next renewal date on. A refused decrease answers 200 with status blocked and the blockers; current_users, users_to_remove and minimum_seats say how far the People list allows the decrease.'
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/SeatChangeRequest'
      responses:
        '200':
          description: The evaluated decrease; status blocked with blockers when it is refused
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SeatChangeResponse'
        '400':
          description: Invalid request payload
        '403':
          description: Not an administrator of the organization
        '500':
          description: The People count or the settings could not be read
  '/organizations/{organizationId}/seat-change/confirm':
    post:
      summary: Schedule a seat decrease for the next renewal
      description: 'Stores the decrease as the organization''s pending seat change (one per organization; a new confirmation replaces it). Requires current_seats, the committed seats the admin saw in the preview. Idempotent on request_id. The requester is taken from the caller''s token.'
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/SeatChangeRequest'
      responses:
        '200':
          description: The scheduled decrease (or the stored one for a repeated request_id)
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SeatChangeResponse'
        '400':
          description: 'Invalid request payload, or blocked (the body then lists the blockers)'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SeatChangeResponse'
        '403':
          description: Not an administrator of the organization
        '409':
          description: 'current_seats is stale, request_id was used for another seat change, or the seats or the pending decrease changed while confirming (preview again)'
        '500':
          description: The People count or the settings could not be read
  '/organizations/{organizationId}/seat-change':
    delete:
      summary: Cancel the pending seat decrease
      description: 'Withdraws the seat decrease scheduled for the next renewal before it is applied, so the organization renews with its current seats.'
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: 'The canceled change, with status canceled'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SeatChangeResponse'
        '403':
          description: Not an administrator of the organization
        '404':
          description: No pending seat change
        '409':
          description: The pending seat change was canceled or replaced while canceling (reload)
        '500':
          description: The settings could not be read or written
  '/organizations/{organizationId}/devices':
    get:
      summary: Returns all devices grouped by organization for users
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: organizationId
          required: true
          schema:
            type: string
        - in: query
          name: email
          description: email
          required: true
          schema:
            type: string
        - in: query
          name: policyId
          description: policyId
          required: false
          schema:
            type: string
        - in: query
          name: add_cves
          description: add_cves
          required: false
          schema:
            type: string
        - in: query
          name: use_decisions
          description: Include evaluation decisions in the response
          required: false
          schema:
            type: string
      responses:
        '200':
          description: Returns all devices grouped by organization for users
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Shadow'
  '/organizations/{organizationId}/devices/{deviceId}':
    get:
      summary: Get a specific device by ID
      tags:
        - Devices
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: deviceId
          description: ID of Device
          required: true
          schema:
            type: string
        - in: query
          name: policyId
          description: Policy ID for evaluation
          required: false
          schema:
            type: string
        - in: query
          name: add_cves
          description: Include CVE information
          required: false
          schema:
            type: string
        - in: query
          name: use_decisions
          description: Include evaluation decisions in the response
          required: false
          schema:
            type: string
      responses:
        '200':
          description: Device found
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Shadow'
        '403':
          description: 'Forbidden - not authorized, or the device is a discovered device whose details the organization''s plan does not include (hide_discovered_device_details). The latter answers with error `discovered_device_details_not_in_plan`; the device lists still carry the device, with details_hidden, issues_count and risk.'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '404':
          description: Device not found
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '500':
          description: Server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
    patch:
      summary: Update device/shadow metadata
      tags:
        - Devices
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: deviceId
          description: ID of Device
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                note:
                  type: string
                  description: Note to add to the device
                tags:
                  type: array
                  items:
                    type: string
                  description: Tags to associate with the device
              additionalProperties: false
      responses:
        '204':
          description: Device metadata updated successfully
        '400':
          description: Bad request
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '403':
          description: Forbidden - not authorized
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '404':
          description: Device not found
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '500':
          description: Server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
  '/organizations/{organizationId}/devices/{deviceId}/snooze':
    parameters:
      - in: path
        name: organizationId
        description: ID of Organization
        required: true
        schema:
          type: string
      - in: path
        name: deviceId
        description: ID of Device
        required: true
        schema:
          type: string
    post:
      summary: Snooze a device
      description: |
        Temporarily suppress manual risk and verification emails for a device
        until the provided `snoozed_until` timestamp.
      tags:
        - Devices
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - snoozed_until
              properties:
                snoozed_until:
                  type: integer
                  format: int64
                  description: 'Absolute future timestamp, in seconds since epoch.'
                time_zone:
                  type: string
                  nullable: true
                  description: Optional IANA timezone identifier used by the dashboard when computing custom or preset snooze dates.
                reason:
                  type: string
                  nullable: true
                  maxLength: 500
                  description: Optional reason for the snooze.
                snooze_mfa:
                  type: boolean
                  default: false
                  description: Whether MFA prompts should also be snoozed. Defaults to false when omitted.
              additionalProperties: false
      responses:
        '200':
          description: Device snoozed
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Shadow'
        '400':
          description: Invalid snooze timestamp
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '403':
          description: Not an admin
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '404':
          description: Device not found
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '500':
          description: Server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
    delete:
      summary: Unsnooze a device
      tags:
        - Devices
      responses:
        '204':
          description: Device unsnoozed
        '403':
          description: Not an admin
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '404':
          description: Device not found
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '500':
          description: Server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
  '/organizations/{organizationId}/devices/{deviceId}/send-verification-request':
    post:
      summary: Send Verification Request for device
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: organizationId
          required: true
          schema:
            type: string
        - in: path
          name: deviceId
          description: deviceId
          required: true
          schema:
            type: string
        - in: query
          name: policyId
          description: policyId
          required: false
          schema:
            type: string
      requestBody:
        required: false
        content:
          application/json:
            schema:
              type: object
              properties:
                send_email:
                  type: boolean
                  default: true
                send_slack_message:
                  type: boolean
                  default: false
                send_teams_message:
                  type: boolean
                  default: false
      responses:
        '200':
          description: Verification request sent
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ManualAwarenessSendResponse'
  '/organizations/{organizationId}/devices/{deviceId}/send-risk-request':
    post:
      summary: Send Risk Request for device
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: organizationId
          required: true
          schema:
            type: string
        - in: path
          name: deviceId
          description: deviceId
          required: true
          schema:
            type: string
        - in: query
          name: policyId
          description: policyId
          required: false
          schema:
            type: string
      requestBody:
        required: false
        content:
          application/json:
            schema:
              type: object
              properties:
                send_email:
                  type: boolean
                  default: true
                send_slack_message:
                  type: boolean
                  default: false
                send_teams_message:
                  type: boolean
                  default: false
      responses:
        '200':
          description: Risk request sent
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ManualAwarenessSendResponse'
  '/organizations/{organizationId}/dashboard-users':
    get:
      summary: Get dashboard users of an organization
      description: Get dashboard users of an organization
      tags:
        - organizations
      parameters:
        - in: path
          name: organizationId
          description: The id of the organization
          required: true
          schema:
            type: string
        - in: query
          name: email
          description: The email of the dashboard user
          required: false
          schema:
            type: string
      responses:
        '200':
          description: The dashboard users of the organization
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/DashboardUser'
    put:
      summary: Update a dashboard user of an organization
      description: Update a dashboard user of an organization
      tags:
        - organizations
      parameters:
        - in: path
          name: organizationId
          description: The id of the organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/DashboardUser'
      responses:
        '204':
          description: The dashboard user has been updated
    patch:
      summary: Patch a dashboard user's preferences
      description: Patch mutable preference fields (suggested tasks state and/or messaging prompt dismissed)
      tags:
        - organizations
      parameters:
        - in: path
          name: organizationId
          description: The id of the organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - email
              properties:
                email:
                  type: string
                suggested_tasks_state:
                  type: string
                messaging_prompt_dismissed:
                  type: boolean
      responses:
        '204':
          description: Dashboard user preferences updated
  '/organizations/{organizationId}/users':
    get:
      summary: Get users of an organization
      description: Get a list of all users in an organization with their roles
      tags:
        - organizations
      parameters:
        - in: path
          name: organizationId
          description: The id of the organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: List of users in the organization
          content:
            application/json:
              schema:
                type: object
                properties:
                  users:
                    type: array
                    items:
                      type: object
                      properties:
                        email:
                          type: string
                          description: User email address
                        role:
                          type: string
                          description: User role (admin or empty for regular user)
        '403':
          description: Forbidden - not authorized
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '500':
          description: Internal server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
    post:
      summary: Invite a user to an organization
      description: Invite a user to an organization as an admin. Sends an invitation email to the invitee.
      tags:
        - organizations
      parameters:
        - in: path
          name: organizationId
          description: The id of the organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                invitee:
                  type: string
                  description: The email address of the user to invite
                role_type:
                  type: string
                  description: The role type for the user (optional)
              required:
                - invitee
      responses:
        '204':
          description: The invitation has been sent successfully
        '400':
          description: Bad request
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '403':
          description: Forbidden - not authorized
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '500':
          description: Internal server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
    delete:
      summary: Delete a dashboard user of an organization
      description: Delete a dashboard user of an organization
      tags:
        - organizations
      parameters:
        - in: path
          name: organizationId
          description: The id of the organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - email
              properties:
                email:
                  type: string
                  description: The email of the dashboard user to delete
      responses:
        '204':
          description: The dashboard user has been deleted
  '/organizations/{organizationsId}/full':
    get:
      summary: Request organization information with full details
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationsId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns the organization
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/OrganizationFull'
  '/organizations/{organizationId}/applications/{applicationId}':
    put:
      summary: Update an application
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: applicationId
          description: ID of Application
          required: true
          schema:
            type: string
      requestBody:
        required: true
        description: 'When the application contains inline policies, per-OS version overrides use the same presence semantics as policy PUT: omitted preserves, null clears and inherits from os, an empty object explicitly disables, and a non-empty object replaces the override.'
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Application'
      responses:
        '200':
          description: Application updated
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Application'
    delete:
      summary: Delete an application
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: applicationId
          description: ID of Application
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Application deleted
  '/organizations/{organizationId}/applications/{applicationId}/connect':
    post:
      summary: Connect an application
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: applicationId
          description: ID of Application
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/ApplicationConnect'
      responses:
        '200':
          description: Application connected
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ConnectionError'
  '/organizations/{organizationId}/applications/{applicationId}/connect-app-only':
    post:
      summary: Connect a Microsoft application using the app-only flow
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: applicationId
          description: ID of Application
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                TenantId:
                  type: string
                  format: uuid
                  description: Entra tenant ID
              required:
                - TenantId
      responses:
        '200':
          description: Application connected
  '/organizations/{organizationId}/policies':
    get:
      summary: Request policy information
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns the policy
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Policies'
    post:
      summary: Create a new policy
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Policies'
      responses:
        '200':
          description: Returns the policy
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Policies'
  '/organizations/{organizationId}/policies/{policyId}':
    get:
      summary: Request policy information
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: policyId
          description: ID of Policy
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns the policy
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Policies'
    put:
      summary: Update a policy
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: policyId
          description: ID of Policy
          required: true
          schema:
            type: string
      requestBody:
        required: true
        description: 'Updates the policy while preserving JSON presence for per-OS version overrides. Omitting windows_os, macos_os, linux_os, android_os, ios_os or ipados_os preserves its current value; null clears that override and resumes inheritance from os; an empty object explicitly disables that OS version check; a non-empty object replaces it with a custom override.'
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Policies'
      responses:
        '200':
          description: Policy updated
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Policies'
    delete:
      summary: Delete a policy
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: policyId
          description: ID of Policy
          required: true
          schema:
            type: string
      responses:
        '204':
          description: Policy deleted
  '/organizations/{organizationId}/applications/dashboard-demo':
    get:
      summary: Get dashboard demo
      tags:
        - Demo
      x-internal: true
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns the dashboard demo
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Application'
  '/organizations/{organizationId}/idp-users':
    get:
      summary: List provisioned IdP users (recovery emails)
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: query
          name: include
          description: |
            "enrollment" adds enrolled (bool, or null when identity could not be asked) to every user.
          required: false
          schema:
            type: string
            enum:
              - enrollment
      responses:
        '200':
          description: List of provisioned IdP users
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/IdpUserResponse'
  '/organizations/{organizationId}/idp-users/import':
    post:
      summary: Bulk import IdP users (Google Admin user export)
      description: |
        Creates or updates up to 500 IdP users (email + recovery email) in one request; created users get source "import". Emails are trimmed and lower-cased. Rows whose email domain is not on the organization's IdP connection allow-list (exact, case-insensitive), malformed or repeated rows are reported as invalid and never written. Each row is enriched with the current recovery email, whether the user already enrolled, and when a link was last sent. Imported users count as users: an import that would take the organization past its user limit (trial limit, or licensed seats) is rejected with 409 user_limit_exceeded before anything is written; a dry run instead returns 200 with every row, the seats and exceeded=true. When the limit cannot be checked (billing settings unavailable, or a known limit with the current users unavailable) the request fails closed with 503 seat_check_unavailable, dry runs included. With dry_run nothing is written and the response previews the outcome. Requires an organization administrator.
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/IdpUsersImportRequest'
      responses:
        '200':
          description: Per-row results (or preview) and the seat summary
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IdpUsersImportResponse'
        '400':
          description: 'invalid_json, no_users or too_many_users'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IdpUsersErrorResponse'
        '403':
          description: Not authorized
        '404':
          description: organization_not_found
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IdpUsersErrorResponse'
        '409':
          description: 'idp_connection_required, multiple_idp_connections, or (real runs only) user_limit_exceeded with current, adding and limit'
          content:
            application/json:
              schema:
                oneOf:
                  - $ref: '#/components/schemas/IdpUsersErrorResponse'
                  - $ref: '#/components/schemas/IdpUsersUserLimitExceededResponse'
        '503':
          description: 'seat_check_unavailable: the user limit could not be checked; try again later'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IdpUsersErrorResponse'
  '/organizations/{organizationId}/idp-users/onboarding-links':
    post:
      summary: Queue emailed onboarding links for many IdP users
      description: |
        Classifies each requested user (up to 500) and queues an onboarding-link email for the sendable ones; a worker mints, emails and records each link shortly after, re-checking right before minting that the user has not enrolled meanwhile. Skipped users are reported with their reason: not_provisioned, no_recovery_email, already_enrolled, enrollment_unknown (identity could not be asked; skipped to fail closed), recently_sent (a link went out less than 7 days ago, unless resend_recent) or invalid_email. Returns 202 because queued users have not been emailed yet. Requires an organization administrator.
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/IdpUsersOnboardingLinksRequest'
      responses:
        '202':
          description: Users classified; sendable ones queued
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IdpUsersOnboardingLinksResponse'
        '400':
          description: 'invalid_json, no_emails or too_many_emails'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IdpUsersErrorResponse'
        '403':
          description: Not authorized
        '404':
          description: organization_not_found
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IdpUsersErrorResponse'
        '409':
          description: idp_connection_required or multiple_idp_connections
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IdpUsersErrorResponse'
  '/organizations/{organizationId}/idp-users/{email}':
    put:
      summary: Set or update an IdP user's recovery email
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: email
          description: The IdP user's email
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/SetIdpUserRecoveryEmailRequestBody'
      responses:
        '200':
          description: IdP user upserted
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IdpUserResponse'
    delete:
      summary: Remove an IdP user's recovery email
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: email
          description: The IdP user's email
          required: true
          schema:
            type: string
      responses:
        '204':
          description: IdP user removed
  '/organizations/{organizationId}/idp-users/{email}/onboarding-password':
    post:
      summary: Mint a one-time admin-relayed onboarding password for a provisioned IdP user
      description: |
        Mints a high-entropy onboarding password for a provisioned IdP user who has no reusable MFA factor yet, so a brand-new device can bootstrap first-device passwordless IdP onboarding. The plaintext is returned exactly once (only its digest is stored); an admin relays it to the user out of band. Requires an organization administrator (RBAC). Returns 404 when the user is not a provisioned IdP user (no existence leak) and 409 when the user already has a reusable MFA factor.
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: email
          description: The IdP user's email
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Onboarding password minted
          content:
            application/json:
              schema:
                type: object
                description: 'A one-time admin-relayed onboarding password, returned exactly once'
                properties:
                  password:
                    type: string
                    description: 'The generated onboarding password. Only its digest is stored, so it cannot be retrieved again.'
                  expiresAt:
                    type: integer
                    format: int64
                    description: Unix epoch seconds after which the password stops working
                required:
                  - password
                  - expiresAt
        '403':
          description: Not authorized
        '404':
          description: not_provisioned (IdP user not found)
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IdpUsersErrorResponse'
        '409':
          description: already_enrolled (user already has a reusable MFA factor)
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IdpUsersErrorResponse'
  '/organizations/{organizationId}/idp-users/{email}/onboarding-link':
    post:
      summary: Email a single-use onboarding magic link to a provisioned IdP user
      description: |
        Mints a single-use onboarding-link token for a provisioned IdP user who has no reusable MFA factor yet and EMAILS a magic link to the user's secondary/recovery email, so a brand-new device can bootstrap first-device passwordless IdP onboarding. This is the PREFERRED first-device path; the onboarding-password endpoint is the admin-relayed fallback. The token is never returned in the response — it lives only inside the emailed link (only its digest is stored). Requires an organization administrator (RBAC). Returns 404 when the user is not a provisioned IdP user (no existence leak), 409 when the user already has a reusable MFA factor, and 409 when the organization has no identity-provider application configured or more than one (ambiguous).
      x-internal: true
      tags:
        - Organizations
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: email
          description: The IdP user's email
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Onboarding magic link minted and emailed
          content:
            application/json:
              schema:
                type: object
                description: |
                  Confirmation that a single-use onboarding magic link was minted and emailed. The token is deliberately omitted — it exists only inside the emailed link.
                properties:
                  expiresAt:
                    type: integer
                    format: int64
                    description: Unix epoch seconds after which the emailed onboarding link stops working
                  sentTo:
                    type: string
                    description: Masked hint of the recovery address the link was emailed to (e.g. r***@example.com)
                required:
                  - expiresAt
                  - sentTo
        '403':
          description: Not authorized
        '404':
          description: not_provisioned (IdP user not found) or organization_not_found
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IdpUsersErrorResponse'
        '409':
          description: 'already_enrolled, idp_connection_required or multiple_idp_connections'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IdpUsersErrorResponse'
  '/organizations/{organizationId}/invitations':
    get:
      summary: Get all invitations for an organization
      x-internal: true
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
          description: The ID of the organization
      responses:
        '200':
          description: List of invitations
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/InvitationInformationWithoutTokenResponse'
      patch:
        summary: Update an invitation
        x-internal: true
        tags:
          - Organizations
        parameters:
          - name: organizationId
            in: path
            required: true
  '/organizations/{organizationId}/invitation-token':
    parameters:
      - in: path
        name: organizationId
        required: true
        schema:
          type: string
    get:
      summary: Get the organization's invitation token for managed deployment
      tags:
        - Organizations
      responses:
        '200':
          description: Current invitation token
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/InvitationTokenResponse'
        '404':
          description: 'Organization not found, or no invitation token exists'
    post:
      summary: Issue a new invitation token for managed deployment
      description: 'Always issues a new token, which invalidates every deployment command that already carries the old one. Read the current token with GET first.'
      tags:
        - Organizations
      responses:
        '200':
          description: Issued invitation token
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/InvitationTokenResponse'
        '404':
          description: Organization not found
    delete:
      summary: Revoke the organization's invitation token
      tags:
        - Organizations
      responses:
        '204':
          description: Invitation token revoked
        '404':
          description: Organization not found
  '/organizations/{organizationId}/invitations/{email}':
    put:
      summary: Resend an invitation to a user by email
      x-internal: true
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
          description: The ID of the organization
        - name: email
          in: path
          required: true
          schema:
            type: string
          description: The email address of the invitation
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/InvitationResendRequest'
      responses:
        '200':
          description: Invitation resent successfully
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/InvitationInformationWithoutTokenResponse'
        '400':
          description: Invalid request
        '404':
          description: Invitation not found
    patch:
      summary: Update an invitation for a user by email
      x-internal: true
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
          description: The ID of the organization
        - name: email
          in: path
          required: true
          schema:
            type: string
          description: The email address of the invitation
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/InvitationUpdateRequest'
      responses:
        '204':
          description: Invitation updated successfully
        '400':
          description: Invalid request
        '404':
          description: Invitation not found
  '/organizations/{organizationId}/snapshots':
    get:
      summary: Return snapshots for organization
      tags:
        - Snapshots
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: query
          name: startDate
          description: Start date
          required: false
          schema:
            type: integer
            format: int64
        - in: query
          name: endDate
          description: End date
          required: false
          schema:
            type: integer
            format: int64
      responses:
        '200':
          description: Returns list of snapshots for organization
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/Snapshot'
        '204':
          description: No content
          content:
            application/json:
              schema:
                type: object
                properties:
                  message:
                    type: string
  '/organizations/{organizationId}/shadow-snapshots':
    get:
      summary: Return shadow snapshots for organization
      tags:
        - Snapshots
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: query
          name: policyId
          description: ID of Policy
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns list of shadow snapshots for organization
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ShadowSnapshot'
        '400':
          description: Bad request
          content:
            application/json:
              schema: null
  /agent-adoption:
    get:
      summary: Return fleet-wide XFA agent adoption history
      description: |-
        Returns the daily agent adoption aggregates, oldest first. System administrators only: the aggregate spans the whole fleet and is not scoped to any organization.
        History starts at the day the aggregation job first ran, because the underlying shadow holds only a device's current state and earlier days cannot be recomputed. An empty list is therefore a normal answer.
      tags:
        - Snapshots
      parameters:
        - in: query
          name: days
          description: 'Number of trailing daily aggregates to return, today included. Defaults to 90. Values above 1095 are accepted and clamped to 1095 rather than rejected, which is why no maximum is declared here: a maximum would describe them as invalid input, and they are not.'
          required: false
          schema:
            type: integer
            minimum: 1
            default: 90
            example: 90
      responses:
        '200':
          description: 'Returns the agent adoption aggregates, oldest first'
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/AgentAdoption'
        '400':
          description: Bad request
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '401':
          description: Not authorized
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '403':
          description: MFA required
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '500':
          description: Internal server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
  '/organizations/{organizationId}/configs':
    get:
      summary: Request phishing configs for organization
      x-internal: true
      tags:
        - Phishing Configs
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns the phishing configs
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ConfigsList'
        '403':
          description: User is not authorized for this organization
        '500':
          description: Internal server error
    post:
      summary: Create a new phishing config
      x-internal: true
      tags:
        - Phishing Configs
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/ConfigFields'
      responses:
        '201':
          description: Returns the created phishing config
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Config'
        '400':
          description: Invalid request body
        '403':
          description: User is not authorized for this organization
        '500':
          description: Internal server error
  '/organizations/{organizationId}/configs/{configId}':
    get:
      summary: Request a specific phishing config
      x-internal: true
      tags:
        - Phishing Configs
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: configId
          description: ID of the phishing config
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns the phishing config
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Config'
        '400':
          description: Missing config id
        '403':
          description: User is not authorized for this organization
        '500':
          description: Internal server error
    put:
      summary: Update a phishing config
      x-internal: true
      tags:
        - Phishing Configs
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: configId
          description: ID of the phishing config
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/ConfigFields'
      responses:
        '200':
          description: Returns the updated phishing config fields
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ConfigFields'
        '400':
          description: Invalid request body or missing config id
        '403':
          description: User is not authorized for this organization
        '500':
          description: Internal server error
    delete:
      summary: Delete a phishing config
      x-internal: true
      tags:
        - Phishing Configs
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: configId
          description: ID of the phishing config
          required: true
          schema:
            type: string
      responses:
        '204':
          description: Phishing config deleted successfully
        '400':
          description: Missing config id
        '403':
          description: User is not authorized for this organization
        '500':
          description: Internal server error
  '/organizations/{organizationId}/domain-configs':
    get:
      summary: Request domain configs for organization
      x-internal: true
      tags:
        - Phishing Configs
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns the domain configs
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ConfigsList'
        '403':
          description: User is not authorized for this organization
        '500':
          description: Internal server error
    post:
      summary: Create a new domain config
      x-internal: true
      tags:
        - Phishing Configs
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/ConfigFields'
      responses:
        '201':
          description: Returns the created domain config
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Config'
        '400':
          description: Invalid request body
        '403':
          description: User is not authorized for this organization
        '500':
          description: Internal server error
  '/organizations/{organizationId}/domain-configs/{configId}':
    put:
      summary: Update a domain config
      x-internal: true
      tags:
        - Phishing Configs
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: configId
          description: ID of the domain config
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/ConfigFields'
      responses:
        '200':
          description: Returns the updated domain config fields
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ConfigFields'
        '400':
          description: Invalid request body or missing config id
        '403':
          description: User is not authorized for this organization
        '500':
          description: Internal server error
    delete:
      summary: Delete a domain config
      x-internal: true
      tags:
        - Phishing Configs
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: configId
          description: ID of the domain config
          required: true
          schema:
            type: string
      responses:
        '204':
          description: Domain config deleted successfully
        '400':
          description: Missing config id
        '403':
          description: User is not authorized for this organization
        '500':
          description: Internal server error
  '/organizations/{organizationId}/dns-verification/latest':
    get:
      summary: Get latest DNS verification results for organization
      x-internal: true
      tags:
        - Phishing Configs
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns the latest DNS verification results
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/DomainVerificationResult'
        '403':
          description: User is not authorized for this organization
        '500':
          description: Internal server error
  '/organizations/{organizationId}/dns-verification/domains/{domain}/history':
    get:
      summary: Get DNS verification history for a domain
      x-internal: true
      tags:
        - Phishing Configs
      parameters:
        - in: path
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
        - in: path
          name: domain
          description: Domain name
          required: true
          schema:
            type: string
        - in: query
          name: limit
          description: Maximum number of results to return
          required: false
          schema:
            type: integer
      responses:
        '200':
          description: Returns the DNS verification history for the domain
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/DomainVerificationResult'
        '400':
          description: Missing domain or invalid limit parameter
        '403':
          description: User is not authorized for this organization
        '500':
          description: Internal server error
  /roles:
    get:
      summary: Returns roles with information for user
      x-internal: true
      tags:
        - Roles
      responses:
        '200':
          description: Returns roles for user
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/RoleList'
  '/public/referral/{referralCode}':
    parameters:
      - name: referralCode
        in: path
        required: true
        description: 'A user''s referral code, from a ?ref= link.'
        schema:
          type: string
    get:
      tags:
        - Referral
      summary: Resolve a referral code to the referrer's first name
      description: |
        Public (unauthenticated) endpoint for the referral landing page. Returns
        only the referrer's first name. Every failure answers 404 so the page falls
        back to a name-less hero and the endpoint cannot be used to probe.
      security: []
      responses:
        '200':
          description: The referrer's first name
          content:
            application/json:
              schema:
                type: object
                properties:
                  first_name:
                    type: string
                required:
                  - first_name
        '400':
          description: No referral code supplied
        '404':
          description: Referral code unknown or no name available
  /single-discovery:
    post:
      summary: Create a single discovery request
      x-internal: true
      tags:
        - Organizations
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/SingleDiscoveryRequest'
      responses:
        '201':
          description: Single discovery request created
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SingleDiscoveryResponse'
  /transactions:
    get:
      summary: Get transactions
      x-internal: true
      tags:
        - Transactions
      parameters:
        - in: query
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Returns all transactions
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ListTransactions'
  '/transactions/{transactionId}':
    put:
      summary: Approve transaction
      x-internal: true
      tags:
        - Transactions
      parameters:
        - in: path
          name: transactionId
          description: ID of Transaction
          required: true
          schema:
            type: string
        - in: query
          name: organizationId
          description: ID of Organization
          required: true
          schema:
            type: string
      responses:
        '204':
          description: Approved transaction
  /users/details:
    get:
      summary: Get user details
      description: |
        Get user details. Users can get their own details without organizationId.
        To get another user's details, organizationId is required and the requester must have access to that organization.
      x-internal: true
      tags:
        - UsersDetails
      parameters:
        - in: query
          name: user
          description: email of the user
          required: true
          schema:
            type: string
        - in: query
          name: organizationId
          description: 'Organization ID (required when getting another user''s details, optional when getting own details)'
          required: false
          schema:
            type: string
      responses:
        '200':
          description: User details
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/UserDetails'
        '400':
          description: Bad request (missing required parameters)
        '403':
          description: Forbidden (insufficient permissions)
    patch:
      summary: Update user details
      description: |
        Update user details. Authorization depends on what fields are being updated:
        - Language, FirstName, LastName: Only the user themselves can update (email must match)
        - Groups: Only organization admins and super admins can update (organizationId required for org admins)
      x-internal: true
      tags:
        - UsersDetails
      parameters:
        - in: query
          name: user
          description: email of the user
          required: true
          schema:
            type: string
        - in: query
          name: organizationId
          description: 'Organization ID (required when updating groups for organization admins, optional for super admins)'
          required: false
          schema:
            type: string
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/UserDetails'
      responses:
        '204':
          description: User details updated successfully
        '400':
          description: Bad request (missing required parameters or validation error)
        '403':
          description: Forbidden (insufficient permissions)
  /users/revoke:
    post:
      summary: Revoke user sessions
      description: |
        Revoke all sessions for a user, invalidating their previous authentication tokens.
        Users can revoke their own sessions without organizationId.
        Administrators can revoke any user's sessions within their organization (organizationId required).
      x-internal: true
      tags:
        - UsersDetails
      parameters:
        - in: query
          name: user
          description: email of the user whose sessions should be revoked
          required: true
          schema:
            type: string
        - in: query
          name: organizationId
          description: 'Organization ID (required when revoking another user''s sessions, optional when revoking own sessions)'
          required: false
          schema:
            type: string
      responses:
        '204':
          description: User sessions revoked successfully
        '400':
          description: Bad request (missing required parameters)
        '403':
          description: Forbidden (insufficient permissions)
  '/organizations/{organizationId}/admin-mfa-approval/setting':
    get:
      summary: Get organization-wide administrator MFA approval setting
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Current setting
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/AdminMfaApprovalSetting'
        '404':
          description: Organization not found or capability unavailable
  '/organizations/{organizationId}/admin-mfa-approval/setting/enable':
    post:
      summary: Enable organization-wide administrator MFA approval
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/AdminMfaApprovalSettingMutation'
      responses:
        '200':
          description: Setting enabled
          content:
            application/json:
              schema:
                type: object
                required:
                  - guard_id
                  - setting
                properties:
                  guard_id:
                    type: string
                  setting:
                    $ref: '#/components/schemas/AdminMfaApprovalSetting'
        '400':
          description: Invalid request
        '404':
          description: Organization not found
        '409':
          description: 'Stale setting version, missing administrator device, or application eligibility violations'
          content:
            application/json:
              schema:
                oneOf:
                  - $ref: '#/components/schemas/AdminMfaApprovalEligibilityConflict'
                  - $ref: '#/components/schemas/AdminMfaApprovalConflict'
  '/organizations/{organizationId}/admin-mfa-approval/setting/disable':
    post:
      summary: Disable organization-wide administrator MFA approval
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/AdminMfaApprovalSettingDisableMutation'
      responses:
        '202':
          description: Disable reconciliation accepted and the matching application guard released.
          content:
            application/json:
              schema:
                type: object
                required:
                  - state
                  - setting_version
                  - guard_id
                properties:
                  state:
                    type: string
                    enum:
                      - DISABLING
                      - 'OFF'
                  setting_version:
                    type: integer
                    format: int64
                  guard_id:
                    type: string
                    format: uuid
        '400':
          description: Invalid request
        '404':
          description: Organization not found
        '409':
          description: 'Stale setting version, mismatched guard identifier, or a held application guard'
          content:
            application/json:
              schema:
                oneOf:
                  - $ref: '#/components/schemas/AdminMfaApprovalEligibilityConflict'
                  - $ref: '#/components/schemas/AdminMfaApprovalConflict'
  '/organizations/{organizationId}/admin-mfa-approval/setting/auto-approve-managed':
    post:
      summary: Turn automatic approval of managed devices on or off
      description: Only while organization-wide administrator MFA approval is ACTIVE. Affects new approvals only; existing approvals keep their status.
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/AdminMfaApprovalAutoApproveManagedMutation'
      responses:
        '200':
          description: Updated setting
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/AdminMfaApprovalSetting'
        '400':
          description: Invalid request
        '404':
          description: Organization not found or capability unavailable
        '409':
          description: 'Approval is not active, or the setting changed concurrently'
  '/organizations/{organizationId}/admin-mfa-approval/approvals':
    get:
      summary: List administrator MFA approvals by descending activity
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
        - name: status
          in: query
          schema:
            type: string
            enum:
              - PENDING
              - APPROVED
              - REJECTED
        - name: limit
          in: query
          schema:
            type: integer
            minimum: 1
            maximum: 100
            default: 25
        - name: cursor
          in: query
          schema:
            type: string
      responses:
        '200':
          description: Approval activity page
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/AdminMfaApprovalPage'
        '400':
          description: 'Invalid filter, limit, or cursor'
        '404':
          description: Organization not found or capability unavailable
  '/organizations/{organizationId}/admin-mfa-approval/pending-count':
    get:
      summary: Count administrator MFA approval requests that wait for a decision
      description: 'Counts requested approvals that are still pending, without listing them. Approvals that were bound but never requested are not counted.'
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
      responses:
        '200':
          description: Pending request count
          content:
            application/json:
              schema:
                type: object
                required:
                  - count
                properties:
                  count:
                    type: integer
                    minimum: 0
        '404':
          description: Organization not found or capability unavailable
  '/organizations/{organizationId}/admin-mfa-approval/approvals/{approvalId}/approve':
    post:
      operationId: approveAdminMfaApproval
      summary: Transition an administrator MFA approval using revision CAS
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
        - name: approvalId
          in: path
          required: true
          schema:
            type: string
            minLength: 43
            maxLength: 43
            pattern: '^[A-Za-z0-9_-]{43}$'
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/AdminMfaApprovalTransition'
      responses:
        '200':
          description: Updated approval
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/AdminMfaApproval'
        '400':
          description: Invalid transition or missing decline reason
        '404':
          description: Approval not found in this organization or capability unavailable
        '409':
          description: Stale expected revision
  '/organizations/{organizationId}/admin-mfa-approval/approvals/{approvalId}/decline':
    post:
      operationId: declineAdminMfaApproval
      summary: Transition an administrator MFA approval using revision CAS
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
        - name: approvalId
          in: path
          required: true
          schema:
            type: string
            minLength: 43
            maxLength: 43
            pattern: '^[A-Za-z0-9_-]{43}$'
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/AdminMfaApprovalDeclineTransition'
      responses:
        '200':
          description: Updated approval
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/AdminMfaApproval'
        '400':
          description: Invalid transition or missing decline reason
        '404':
          description: Approval not found in this organization or capability unavailable
        '409':
          description: Stale expected revision
  '/organizations/{organizationId}/admin-mfa-approval/approvals/{approvalId}/reapprove':
    post:
      operationId: reapproveAdminMfaApproval
      summary: Transition an administrator MFA approval using revision CAS
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
        - name: approvalId
          in: path
          required: true
          schema:
            type: string
            minLength: 43
            maxLength: 43
            pattern: '^[A-Za-z0-9_-]{43}$'
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/AdminMfaApprovalTransition'
      responses:
        '200':
          description: Updated approval
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/AdminMfaApproval'
        '400':
          description: Invalid transition or missing decline reason
        '404':
          description: Approval not found in this organization or capability unavailable
        '409':
          description: Stale expected revision
  '/organizations/{organizationId}/admin-mfa-approval/approvals/{approvalId}/revoke':
    post:
      operationId: revokeAdminMfaApproval
      summary: Revoke an approved administrator MFA approval using revision CAS
      description: 'Moves an APPROVED approval, including one granted automatically to a device that existed before activation, to REJECTED. The reason is required and is shown to the user on their next sign-in. Issued tokens stay valid until they expire. The user''s silent MFA key on the device is removed; TOTP and passkeys are kept.'
      tags:
        - Organizations
      parameters:
        - name: organizationId
          in: path
          required: true
          schema:
            type: string
        - name: approvalId
          in: path
          required: true
          schema:
            type: string
            minLength: 43
            maxLength: 43
            pattern: '^[A-Za-z0-9_-]{43}$'
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/AdminMfaApprovalDeclineTransition'
      responses:
        '200':
          description: 'Rejected approval, including an already-rejected approval (idempotent)'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/AdminMfaApproval'
        '400':
          description: Missing or invalid revoke reason
        '404':
          description: Approval not found in this organization or capability unavailable
        '409':
          description: Stale expected revision or pending approval
components:
  securitySchemes:
    bearerAuth:
      type: http
      scheme: bearer
      bearerFormat: JWT
  schemas:
    MfaRemoval:
      type: object
      additionalProperties: false
      required:
        - method
        - revision
      properties:
        method:
          type: string
          enum:
            - totp
            - passkey
            - silent
        revision:
          type: string
          minLength: 1
        credentialId:
          type: string
          minLength: 1
          description: 'Unpadded base64url ID; selects one passkey/security key, or one silent MFA registration without a device. Omit to remove the whole method.'
        deviceId:
          type: string
          minLength: 1
          description: Only for silent MFA on one device. Omit both deviceId and credentialId to remove all silent MFA for this user.
    MfaSummary:
      type: object
      required:
        - totp
        - passkeys
        - silent
        - passkeysRevision
        - silentRevision
      properties:
        totp:
          $ref: '#/components/schemas/MfaTotp'
        passkeys:
          type: array
          items:
            $ref: '#/components/schemas/MfaRegistration'
        silent:
          type: array
          items:
            $ref: '#/components/schemas/MfaRegistration'
        passkeysRevision:
          type: string
        silentRevision:
          type: string
    MfaTotp:
      type: object
      required:
        - enabled
        - setupPending
        - revision
      properties:
        enabled:
          type: boolean
        setupPending:
          type: boolean
        revision:
          type: string
    MfaRegistration:
      type: object
      required:
        - id
        - authenticatorType
        - revision
      properties:
        id:
          type: string
        authenticatorType:
          type: string
        deviceId:
          type: string
        revision:
          type: string
    ActiveUsers:
      type: object
      properties:
        current_insight:
          type: integer
          description: Current insight users count
        last_insight:
          type: integer
          description: Last insight users count
        current_connect:
          type: integer
          description: Current connect users count
        last_connect:
          type: integer
          description: Last connect users count
        current_user_count:
          type: integer
          description: Current total users count
        last_user_count:
          type: integer
          description: Last total users count
        current_verifications:
          type: integer
          description: 'Enforcement verifications this month: warned + blocked + secure sign-ins + snoozed'
        last_verifications:
          type: integer
          description: Enforcement verifications last month
        current_granted:
          type: integer
          description: Sign-ins an administrator manually granted this month. Not counted as verifications.
        last_granted:
          type: integer
          description: Sign-ins an administrator manually granted last month
        lifetime_verifications:
          type: integer
          description: 'Enforcement verifications since counting started (2025-01-28; secure sign-ins only since 2026-01-26), so a floor'
        year_verifications:
          type: integer
          description: Enforcement verifications since 1 January of the current year (UTC)
        last_7_days_verifications:
          type: integer
          description: Enforcement verifications over the 7 full days before today (UTC). Divide by 7 for the daily rate.
    Affiliation:
      type: object
      properties:
        organization_id:
          type: string
          description: ID of the organization
        email:
          type: string
          description: Email of the user
        device_id:
          type: string
          description: ID of the device
        timestamp:
          type: string
          description: Timestamp of the affiliation
      required:
        - organization_id
        - email
        - device_id
        - timestamp
    Application:
      type: object
      properties:
        organizationID:
          type: string
          description: ID of the organization
        applicationID:
          type: string
          description: ID of the application
        policyID:
          type: string
          description: ID of the policy
        type:
          $ref: '#/components/schemas/Type'
        testKey:
          type: string
          description: Test key
        name:
          type: string
          description: Name of the application
        iconUrl:
          type: string
          description: Icon URL of the application
        policies:
          $ref: '#/components/schemas/Policies'
        allowedApplicationDomainRegexes:
          type: array
          description: Allowed application domain regexes
          items:
            type: string
        publicCerts:
          type: array
          description: Public certificates
          items:
            type: string
        SAMLMetadataUrl:
          type: string
          description: SAML Metadata URL
        SAMLConfiguration:
          $ref: '#/components/schemas/SAMLConfiguration'
        OAuthConfiguration:
          $ref: '#/components/schemas/OAuthConfiguration'
        clientSecret:
          type: string
          description: Client secret
        SSOUrl:
          type: string
          description: SSO URL
        issuer:
          type: string
          description: Issuer
        customSessionDurationInHours:
          type: integer
          description: Custom session duration in hours
        filteredEmail:
          type: array
          description: Filtered email addresses
          items:
            type: string
        filterMobile:
          type: boolean
          description: Filter mobile devices
        filterDesktop:
          type: boolean
          description: Filter desktop devices
        filteredOS:
          type: array
          description: Filtered operating systems
          items:
            type: string
        enableMfa:
          type: boolean
          description: Enable MFA
        enableMfaAutoApproveFirstDevice:
          type: boolean
          description: Enable MFA auto-approve first device
        alwaysVerifyMfa:
          type: boolean
          description: Double Identity Verification
        uniquePurpose:
          type: string
          description: Unique purpose of the application
          enum:
            - DashboardDemo
        enabled:
          type: boolean
          description: Enabled
        allowedEmailDomains:
          type: array
          description: Allowed email-domain allow-list for the IdP connection
          items:
            type: string
        mfaFirst:
          type: boolean
          description: Run passkey/MFA before device posture (IdP connection)
        requireEmailVerification:
          type: boolean
          description: Require recovery-email proof at onboarding (IdP connection)
        IdPProvider:
          type: string
          description: 'Branded provider of an IdP connection, such as a Google Workspace connection. Only valid when type is IdP; unrelated to the Google type (Workspace device discovery). Cannot be cleared once set.'
          enum:
            - Google
          x-enum-varnames:
            - IdPProviderGoogle
        googleConnection:
          $ref: '#/components/schemas/GoogleConnection'
        microsoftConnection:
          $ref: '#/components/schemas/MicrosoftConnection'
        oktaConnection:
          $ref: '#/components/schemas/OktaConnection'
      required:
        - organizationID
        - applicationID
        - name
        - allowedApplicationDomainRegexes
        - publicCerts
        - SAMLMetadataUrl
        - SSOUrl
        - issuer
        - filteredEmail
    ApplicationsList:
      type: object
      properties:
        applications:
          type: array
          items:
            $ref: '#/components/schemas/Application'
    ApplicationConnect:
      type: object
      properties:
        Code:
          type: string
          description: Code
        RedirectURI:
          type: string
          description: Redirect URI
    AdminMfaApprovalSetting:
      type: object
      required:
        - enabled
        - state
        - setting_version
      properties:
        enabled:
          type: boolean
        state:
          type: string
          enum:
            - 'OFF'
            - ENABLING
            - ACTIVE
            - DISABLING
        setting_version:
          type: integer
          format: int64
        guard_id:
          type: string
          format: uuid
          description: Active enable-attempt identifier required as CAS input when disabling.
        auto_approve_managed:
          type: boolean
          description: 'When true, a new approval request is approved automatically after MFA when that exact device is enrolled through XFA MDM. Only new requests are affected.'
    AdminMfaApprovalSettingMutation:
      type: object
      required:
        - expected_setting_version
      additionalProperties: false
      properties:
        expected_setting_version:
          type: integer
          format: int64
          minimum: 0
    AdminMfaApprovalSettingDisableMutation:
      type: object
      required:
        - expected_setting_version
        - guard_id
      additionalProperties: false
      properties:
        expected_setting_version:
          type: integer
          format: int64
          minimum: 1
        guard_id:
          type: string
          format: uuid
          description: Guard identifier returned by the matching successful enable.
    AdminMfaApprovalAutoApproveManagedMutation:
      type: object
      required:
        - enabled
      additionalProperties: false
      properties:
        enabled:
          type: boolean
    AdminMfaApprovalApplication:
      type: object
      required:
        - application_id
      properties:
        application_id:
          type: string
        application_name:
          type: string
    AdminMfaApprovalDecision:
      type: object
      required:
        - actor_id
        - at
      properties:
        actor_id:
          type: string
          description: 'Stable namespaced authenticated principal, never an email address.'
        reason:
          type: string
        at:
          type: string
          format: date-time
    AdminMfaApprovalSummary:
      type: object
      required:
        - approval_id
        - canonical_user_id
        - device_id
        - status
        - revision
        - application
        - updated_at
      properties:
        requester_email:
          type: string
          format: email
          description: Verified sign-in email of the applicant. Omitted when not yet recorded; never inferred from the device owner.
        approval_id:
          type: string
        canonical_user_id:
          type: string
        device_id:
          type: string
        status:
          type: string
          enum:
            - PENDING
            - APPROVED
            - REJECTED
        revision:
          type: integer
          format: int64
        application:
          $ref: '#/components/schemas/AdminMfaApprovalApplication'
        requested_at:
          type: string
          format: date-time
        updated_at:
          type: string
          format: date-time
          description: 'Last change, including a sign-in that refreshes the request context.'
        decided_at:
          type: string
          format: date-time
          description: When an admin (or turning approval off) last decided; absent while never decided.
        rejection_reason:
          type: string
          maxLength: 1000
          description: 'The reason of the latest rejection, only for REJECTED approvals. It is the text the user sees on sign-in; who decided stays out of the list.'
        resolution_source:
          type: string
          enum:
            - MANAGED_DEVICE
            - ADMIN
            - POLICY_OFF
          description: 'What resolved the approval: automatic approval of a managed device, an administrator, or turning approval off. Absent while never decided.'
    AdminMfaApproval:
      allOf:
        - $ref: '#/components/schemas/AdminMfaApprovalSummary'
        - type: object
          required:
            - setting_version
            - grandfathered
            - created_at
          properties:
            setting_version:
              type: integer
              format: int64
            grandfathered:
              type: boolean
            created_at:
              type: string
              format: date-time
            decision:
              $ref: '#/components/schemas/AdminMfaApprovalDecision'
            last_rejection:
              $ref: '#/components/schemas/AdminMfaApprovalDecision'
    AdminMfaApprovalPage:
      type: object
      required:
        - approvals
        - cursor
      properties:
        approvals:
          type: array
          items:
            $ref: '#/components/schemas/AdminMfaApprovalSummary'
        cursor:
          type: string
    AdminMfaApprovalDeviceDetail:
      type: object
      required:
        - status
        - approval_id
        - canonical_user_id
        - revision
      properties:
        status:
          type: string
          enum:
            - PENDING
            - APPROVED
            - REJECTED
        approval_id:
          type: string
        canonical_user_id:
          type: string
        revision:
          type: integer
          format: int64
        last_rejection:
          $ref: '#/components/schemas/AdminMfaApprovalDecision'
    AdminMfaApprovalTransition:
      type: object
      required:
        - expected_revision
      additionalProperties: false
      properties:
        expected_revision:
          type: integer
          format: int64
          minimum: 1
        reason:
          type: string
          maxLength: 1000
    AdminMfaApprovalDeclineTransition:
      type: object
      required:
        - expected_revision
        - reason
      additionalProperties: false
      properties:
        expected_revision:
          type: integer
          format: int64
          minimum: 1
        reason:
          type: string
          minLength: 1
          maxLength: 1000
    AdminMfaApprovalViolation:
      type: object
      required:
        - application_id
        - code
        - field
      properties:
        application_id:
          type: string
        code:
          type: string
          enum:
            - mfa_disabled
            - mfa_method_required
            - oauth_provider_identity_unavailable
            - skip_enabled
            - skip_mobile_enabled
            - skip_desktop_enabled
            - agentless_allowed
        field:
          type: string
    AdminMfaApprovalEligibilityConflict:
      type: object
      required:
        - guard_id
        - state
        - eligible
        - created_at
        - violations
      properties:
        guard_id:
          type: string
        state:
          type: string
        eligible:
          type: boolean
        created_at:
          type: integer
          format: int64
        setting:
          allOf:
            - $ref: '#/components/schemas/AdminMfaApprovalSetting'
          description: Latest setting observed after a failed enable attempt. Wait for OFF before retrying with its setting_version.
        violations:
          type: array
          items:
            $ref: '#/components/schemas/AdminMfaApprovalViolation'
    AdminMfaApprovalConflict:
      type: object
      required:
        - error
      properties:
        error:
          type: string
        code:
          type: string
          enum:
            - admin_device_required
          description: 'Actionable bootstrap requirement, when present.'
    IdpUserResponse:
      type: object
      description: An admin-provisioned IdP user (recovery email for first-device onboarding)
      properties:
        organization_id:
          type: string
          description: ID of the organization
        email:
          type: string
          description: The IdP user's email
        recovery_email:
          type: string
          description: Recovery email the one-time enrollment code is sent to
        timestamp:
          type: string
          description: Creation timestamp
        updated_timestamp:
          type: string
          description: Last-update timestamp
        source:
          type: string
          enum:
            - manual
            - import
          description: How the user was provisioned. Users created before the field existed report "manual".
        link_sent_at:
          type: string
          format: date-time
          description: When an onboarding link was last emailed (RFC3339). Omitted if never sent.
        enrolled:
          type: boolean
          nullable: true
          description: |
            Only with ?include=enrollment: whether the user already has a reusable MFA factor. null when identity could not be asked.
      required:
        - organization_id
        - email
        - recovery_email
    IdpUsersErrorResponse:
      type: object
      description: |
        Error body of the idp-users routes. error is a stable code; message is human-readable and kept for compatibility.
      properties:
        error:
          type: string
          enum:
            - invalid_json
            - no_users
            - too_many_users
            - no_emails
            - too_many_emails
            - not_provisioned
            - already_enrolled
            - idp_connection_required
            - multiple_idp_connections
            - organization_not_found
            - user_limit_exceeded
            - seat_check_unavailable
        message:
          type: string
      required:
        - error
        - message
    IdpUsersUserLimitExceededResponse:
      description: 409 body of an import that would exceed the organization's user limit
      allOf:
        - $ref: '#/components/schemas/IdpUsersErrorResponse'
        - type: object
          properties:
            current:
              type: integer
              description: Distinct users the organization has now
            adding:
              type: integer
              description: New distinct users the import would add
            limit:
              type: integer
              description: The organization's user limit
          required:
            - current
            - adding
            - limit
    IdpUsersImportRequest:
      type: object
      properties:
        dry_run:
          type: boolean
          default: false
          description: 'Preview only: validate, enrich and count seats without writing'
        users:
          type: array
          minItems: 1
          maxItems: 500
          items:
            type: object
            properties:
              email:
                type: string
                description: The IdP sign-in email (trimmed and lower-cased)
              recovery_email:
                type: string
                description: Where the onboarding link is emailed. May equal email.
            required:
              - email
              - recovery_email
      required:
        - users
    IdpUsersImportRow:
      type: object
      properties:
        index:
          type: integer
          description: Position of the user in the request
        email:
          type: string
          description: Normalized email
        recovery_email:
          type: string
          description: Normalized recovery email
        status:
          type: string
          enum:
            - created
            - updated
            - unchanged
            - invalid
          description: 'Outcome; in a dry run, what the import would do'
        error:
          type: string
          enum:
            - missing_email
            - invalid_email
            - missing_recovery_email
            - invalid_recovery_email
            - duplicate_email
            - domain_not_allowed
            - rejected
          description: 'Why an invalid row is not written. rejected = refused by the organizations service, see error_message.'
        error_message:
          type: string
        current_recovery_email:
          type: string
          description: Recovery email before this import; omitted for new users
        enrolled:
          type: boolean
          nullable: true
          description: Whether the user already has a reusable MFA factor; null when unknown or invalid
        link_sent_at:
          type: string
          format: date-time
          description: When an onboarding link was last emailed; omitted if never
      required:
        - index
        - email
        - recovery_email
        - status
        - enrolled
    IdpUsersSeatSummary:
      type: object
      description: |
        Seat impact of an import. Imported users count as users. limit is null when no cap applies; current/adding are null when they could not be computed for an organization without a cap.
      properties:
        current:
          type: integer
          nullable: true
        adding:
          type: integer
          nullable: true
        limit:
          type: integer
          nullable: true
      required:
        - current
        - adding
        - limit
    IdpUsersImportResponse:
      type: object
      properties:
        dry_run:
          type: boolean
        results:
          type: array
          items:
            $ref: '#/components/schemas/IdpUsersImportRow'
        created:
          type: integer
        updated:
          type: integer
        unchanged:
          type: integer
        invalid:
          type: integer
        seats:
          $ref: '#/components/schemas/IdpUsersSeatSummary'
        exceeded:
          type: boolean
          description: |
            Whether the import would take the organization past its user limit. Only a dry run returns true (with every row and seats); a real run over the limit gets 409 user_limit_exceeded instead.
      required:
        - dry_run
        - results
        - created
        - updated
        - unchanged
        - invalid
        - seats
        - exceeded
    IdpUsersOnboardingLinksRequest:
      type: object
      properties:
        emails:
          type: array
          minItems: 1
          maxItems: 500
          items:
            type: string
        resend_recent:
          type: boolean
          default: false
          description: |
            Also queue users whose link was sent less than 7 days ago. Without it the worker also skips a user whose link went out less than 5 minutes before it runs (a duplicate send).
      required:
        - emails
    IdpUsersOnboardingLinksResponse:
      type: object
      properties:
        queued:
          type: integer
          description: Users queued for an emailed onboarding link
        results:
          type: array
          description: 'One entry per distinct normalized email, in request order'
          items:
            type: object
            properties:
              email:
                type: string
              status:
                type: string
                enum:
                  - queued
                  - invalid_email
                  - not_provisioned
                  - no_recovery_email
                  - already_enrolled
                  - enrollment_unknown
                  - recently_sent
                  - enqueue_failed
            required:
              - email
              - status
      required:
        - queued
        - results
    SetIdpUserRecoveryEmailRequestBody:
      type: object
      properties:
        recovery_email:
          type: string
          description: Recovery email the one-time enrollment code is sent to
      required:
        - recovery_email
    AffiliationRequestBody:
      type: object
      properties:
        device_token:
          type: string
          description: Device token
        invitation_token:
          type: string
          description: Invitation token
      required:
        - device_token
        - invitation_token
    AddLicensesRequest:
      type: object
      properties:
        quantity:
          type: integer
          minimum: 1
          maximum: 10000
          description: Number of licenses to add
        request_id:
          type: string
          maxLength: 128
          description: Optional client-supplied idempotency key for retry-safe license additions
      required:
        - quantity
    AddLicensesResponse:
      type: object
      required:
        - message
        - addition_id
        - request_id
      properties:
        message:
          type: string
          description: Human-readable status for the license addition
        addition_id:
          type: string
          description: Stable identifier of the created or existing LicenseAddition record; maps to LicenseAddition.AdditionID in billing settings
        request_id:
          type: string
          description: Idempotency key used for the license addition; maps to LicenseAddition.RequestID in billing settings
    BillingCycle:
      type: string
      enum:
        - monthly
        - yearly
    Billing-Settings:
      type: object
      properties:
        OrganizationID:
          type: string
          description: ID of the organization
        InsightPrice:
          type: number
          format: double
          description: Monthly price for insight
        ConnectPrice:
          type: number
          format: double
          description: Monthly price for connect
        FreeDevices:
          type: integer
          description: Number of free devices
        FreeUsers:
          type: integer
          description: Number of free users for monthly invoices
        TrialUserLimit:
          type: integer
          minimum: 1
          maximum: 10000
          description: Maximum number of distinct users visible during the trial. Defaults to 10 when omitted.
        TrialEndDate:
          type: string
          description: 'End date of the trial period (format: YYYYMMDD)'
        EndDate:
          type: string
          description: 'End date (format: YYYYMMDD)'
        PerUserPrice:
          type: number
          format: double
          nullable: true
          description: Monthly price per user
        BlockedAccess:
          type: boolean
          nullable: true
          description: Whether access is blocked
        TotalYearlyPrice:
          type: number
          format: double
          nullable: true
          description: Total yearly price
        NrOfYearlyLicenses:
          type: integer
          description: Number of yearly licenses
        BillExtraLicenses:
          type: boolean
          description: Whether to bill extra licenses
        StartDate:
          type: string
          description: Start date
        Partner:
          type: string
          description: Partner name
        PayingCustomer:
          type: boolean
          description: Whether the organization is a paying customer
        PaymentPlan:
          $ref: '#/components/schemas/PaymentPlan'
        Currency:
          $ref: '#/components/schemas/Currency'
        PaymentTermInDays:
          type: integer
          description: Payment term in days
        PONumber:
          type: string
          description: Purchase order number
        MinimumMonthlyLicenses:
          type: integer
          description: Minimum number of licenses to bill for monthly invoices
        NrOfMonthlyLicenses:
          type: integer
          description: Fixed number of licenses for monthly billing (enables fixed-license monthly billing instead of usage-based)
        PerUserYearlyPrice:
          type: number
          format: double
          nullable: true
          description: Annual price per user (alternative to TotalYearlyPrice for per-user yearly billing)
        MidCycleLicenseAdditions:
          type: array
          description: Unbilled or historical mid-cycle license additions
          items:
            $ref: '#/components/schemas/LicenseAddition'
        ScheduledSeatChange:
          $ref: '#/components/schemas/SeatChange'
        LastSeatChange:
          $ref: '#/components/schemas/SeatChange'
      required:
        - OrganizationID
    LicenseAddition:
      type: object
      properties:
        AdditionID:
          type: string
          description: Persisted billing-settings identifier for this license addition; add-license responses expose the same value as addition_id
        RequestID:
          type: string
          description: Persisted client idempotency key for this license addition; add-license responses expose the same value as request_id
        AddedDate:
          type: string
          pattern: '^\d{8}(T\d{6})?$'
          description: Date when licenses were requested in legacy 20060102 or current 20060102T150405 format
        Quantity:
          type: integer
          description: Number of licenses added
        PricePerLicense:
          type: number
          format: double
          description: Price per added license for the selected billing cycle
        Billed:
          type: boolean
          description: Whether the addition has been invoiced
        SeatsApplied:
          type: boolean
          description: Whether the added seats have been applied to the billing settings
        BillingCycle:
          $ref: '#/components/schemas/BillingCycle'
        RequestedByEmail:
          type: string
          description: Trusted email of the actor that requested the addition
        RequestedByUserID:
          type: string
          description: Trusted user ID of the actor that requested the addition
    Currency:
      type: string
      enum:
        - EUR
        - USD
        - GBP
      description: Supported currencies
    Frequency:
      type: string
      enum:
        - daily
        - weekly
        - monthly
        - quarterly
        - none
        - on-demand
        - limited
      description: Frequency interval
    PaymentPlan:
      type: object
      properties:
        Name:
          type: string
        NrOfPolicies:
          type: integer
        NrOfDiscovery:
          type: integer
        AwarenessVerificationFrequency:
          $ref: '#/components/schemas/Frequency'
        AwarenessRiskFrequency:
          $ref: '#/components/schemas/Frequency'
        NrOfEnforcement:
          type: integer
        CustomIntegration:
          type: boolean
        AdminSecurityReports:
          $ref: '#/components/schemas/Frequency'
        Cves:
          type: boolean
        Mfa:
          type: boolean
        AdvancedMfa:
          type: boolean
        ExportToGRC:
          type: boolean
        ApplyDuringTrial:
          type: boolean
    PlanChangePricing:
      type: object
      properties:
        currency:
          $ref: '#/components/schemas/Currency'
        unit_price:
          type: number
          format: float
        recurring_amount:
          type: number
          format: float
        billing_cycle:
          $ref: '#/components/schemas/BillingCycle'
    PlanChangeRequest:
      type: object
      properties:
        plan_name:
          type: string
        billing_cycle:
          $ref: '#/components/schemas/BillingCycle'
        seats:
          type: integer
        request_id:
          type: string
          description: 'Optional client-supplied idempotency/request identifier. If omitted, the API Gateway request id is forwarded to billing.'
        checkout_return_url:
          type: string
          description: Optional absolute dashboard URL used as Mollie redirect target after checkout.
      required:
        - plan_name
    PlanChangeResponse:
      type: object
      properties:
        status:
          $ref: '#/components/schemas/PlanChangeStatus'
        message:
          type: string
        error_code:
          type: string
          description: 'Typed reason when billing refuses the checkout a confirm needs, passed through with billing''s 4xx status: billing_email_invalid, checkout_return_url_invalid, checkout_return_url_not_allowed, checkout_request_invalid, payment_method_exists or payment_method_not_found. Absent on other responses.'
          example: billing_email_invalid
        request_id:
          type: string
        change_id:
          type: string
        requested_at:
          type: string
        requested_by_email:
          type: string
        requested_by_user_id:
          type: string
        current_plan_name:
          type: string
        target_plan_name:
          type: string
        current_billing_cycle:
          $ref: '#/components/schemas/BillingCycle'
        target_billing_cycle:
          $ref: '#/components/schemas/BillingCycle'
        current_seats:
          type: integer
        target_seats:
          type: integer
        effective_date:
          type: string
        payment_method_required:
          type: boolean
        pending_checkout:
          type: boolean
          description: True when the target plan is waiting for checkout/payment mandate completion and has not been applied.
        checkout_url:
          type: string
        hubspot_notification_required:
          type: boolean
        internal_notification_required:
          type: boolean
        has_partner_terms:
          type: boolean
        has_discount_terms:
          type: boolean
        pricing:
          $ref: '#/components/schemas/PlanChangePricing'
        upgrade_charge:
          $ref: '#/components/schemas/PlanUpgradeCharge'
        blockers:
          type: array
          items:
            type: string
    PlanChangeStatus:
      type: string
      enum:
        - applied
        - scheduled
        - checkout_required
        - blocked
        - canceled
    PlanUpgradeCharge:
      type: object
      description: 'What a paying organization owes for the rest of its current billing cycle when it upgrades mid-cycle: the unit price difference for the seats it pays for, pro-rated from the day the upgrade was applied to the next renewal, net of its discounts and before VAT. Invoiced by the next daily invoicing run. On a change that still waits for a checkout it is the amount as of the preview; the charge is computed again on the day the change applies.'
      properties:
        change_id:
          type: string
        from_plan:
          type: string
        to_plan:
          type: string
        applied_at:
          type: string
          description: 'When the upgrade took effect, 20060102T150405 UTC'
        cycle_start:
          type: string
          description: 'The first day of the billing cycle the upgrade fell in, 20060102'
        cycle_end:
          type: string
          description: 'The last day of that cycle, 20060102'
        seats:
          type: integer
          description: The seats the difference is charged for (free users left out)
        unit_price_difference:
          type: number
          format: float
        billing_cycle:
          $ref: '#/components/schemas/BillingCycle'
        pro_rata:
          type: number
          format: float
          description: The fraction of the cycle that remained when the upgrade was applied
        amount:
          type: number
          format: float
          description: 'The net amount, discounts applied, before VAT'
        discounts:
          type: object
          properties:
            DiscountPercentage:
              type: number
              format: float
            DiscountCodePercentage:
              type: number
              format: float
            DiscountCodeID:
              type: string
        billed:
          type: boolean
        invoice_date:
          type: string
          description: The key of the invoice once billed; empty when nothing was owed
    PlanOptionsResponse:
      type: object
      properties:
        plans:
          type: array
          items:
            $ref: '#/components/schemas/GlobalPlanDefinition'
        current_plan_name:
          type: string
        current_billing_cycle:
          $ref: '#/components/schemas/BillingCycle'
        current_seats:
          type: integer
        pending_plan_change:
          $ref: '#/components/schemas/ScheduledPlanChange'
        pending_seat_change:
          $ref: '#/components/schemas/SeatChange'
    ScheduledPlanChange:
      type: object
      properties:
        requested_at:
          type: string
        request_id:
          type: string
        change_id:
          type: string
        requested_by_email:
          type: string
        requested_by_user_id:
          type: string
        effective_date:
          type: string
        status:
          $ref: '#/components/schemas/PlanChangeStatus'
        pending_checkout:
          type: boolean
          description: True when the target plan is waiting for checkout/payment mandate completion and has not been applied.
        plan_name:
          type: string
        billing_cycle:
          $ref: '#/components/schemas/BillingCycle'
        seats:
          type: integer
        current_plan_name:
          type: string
        current_billing_cycle:
          $ref: '#/components/schemas/BillingCycle'
        current_seats:
          type: integer
        target_payment_plan:
          $ref: '#/components/schemas/PaymentPlan'
        pricing:
          $ref: '#/components/schemas/PlanChangePricing'
        hubspot_notification_required:
          type: boolean
        internal_notification_required:
          type: boolean
        has_partner_terms:
          type: boolean
        has_discount_terms:
          type: boolean
        upgrade_charge:
          $ref: '#/components/schemas/PlanUpgradeCharge'
    SeatChange:
      type: object
      description: A seat decrease scheduled for the next renewal (ScheduledSeatChange) or the last one that ended (LastSeatChange). seats_removed is what the renewal applies; target_seats is the target as of the request.
      properties:
        requested_at:
          type: string
        request_id:
          type: string
        change_id:
          type: string
        requested_by_email:
          type: string
        requested_by_user_id:
          type: string
        effective_date:
          type: string
        status:
          $ref: '#/components/schemas/SeatChangeStatus'
        billing_cycle:
          $ref: '#/components/schemas/BillingCycle'
        current_seats:
          type: integer
        seats_removed:
          type: integer
        target_seats:
          type: integer
        users_at_request:
          type: integer
        users_at_warning:
          type: integer
        warning_sent_at:
          type: string
        users_at_apply:
          type: integer
        seats_before_apply:
          type: integer
        seats_after_apply:
          type: integer
        ended_at:
          type: string
        pricing:
          $ref: '#/components/schemas/SeatChangePricing'
    SeatChangePricing:
      type: object
      description: 'Per billing cycle: billed seats (seats less free users) times the unit price of the current cycle, before discounts and VAT.'
      properties:
        currency:
          $ref: '#/components/schemas/Currency'
        unit_price:
          type: number
          format: float
        recurring_amount_now:
          type: number
          format: float
        recurring_amount_after:
          type: number
          format: float
    SeatChangeRequest:
      type: object
      properties:
        target_seats:
          type: integer
          minimum: 1
          description: The seat total the admin wants from the next renewal on (not the number to remove)
        current_seats:
          type: integer
          description: 'The committed seats the admin saw (current_seats of the preview). Required on confirm, where a different count answers 409; ignored by the preview.'
        request_id:
          type: string
          maxLength: 128
          description: 'Optional idempotency key (or the Idempotency-Key header). If omitted, the API Gateway request id is forwarded to billing. The requester is always taken from the caller''s token.'
      required:
        - target_seats
    SeatChangeResponse:
      type: object
      properties:
        status:
          $ref: '#/components/schemas/SeatChangeStatus'
        message:
          type: string
        change_id:
          type: string
        request_id:
          type: string
        requested_at:
          type: string
        requested_by_email:
          type: string
        requested_by_user_id:
          type: string
        billing_cycle:
          $ref: '#/components/schemas/BillingCycle'
        current_seats:
          type: integer
          description: Committed seats - the license count plus pending_added_seats
        pending_added_seats:
          type: integer
          description: Seats bought on the current cycle that are not finalized yet
        target_seats:
          type: integer
        seats_removed:
          type: integer
        current_users:
          type: integer
          description: People in the People list (0 when it was not read)
        users_to_remove:
          type: integer
          description: People to remove before target_seats is allowed
        free_users:
          type: integer
        minimum_seats:
          type: integer
          description: 'The lowest target accepted now - the People count, the free users, the plan minimum, 1'
        effective_date:
          type: string
          description: 'The next renewal date, 20060102'
        pricing:
          $ref: '#/components/schemas/SeatChangePricing'
        blockers:
          type: array
          description: 'Why the decrease is refused: not_paying_customer, not_fixed_seat_contract, subscription_not_started, increase_not_allowed_here, below_free_users, below_minimum_seats, users_above_target (with current_users and users_to_remove).'
          items:
            type: string
    SeatChangeStatus:
      type: string
      description: 'One of scheduled, applied, canceled, superseded (stored) or blocked (only reported by a preview or a refused confirmation). billing_seat_change events also use warning.'
    CurrentUserCountResponse:
      type: object
      required:
        - count
      properties:
        count:
          type: integer
          description: 'People in the People list now (users with a device that submitted in the last 30 days, one per email)'
    PlanPricing:
      type: object
      properties:
        monthlyPricePerSeat:
          type: number
          format: float
          nullable: true
        yearlyPricePerSeat:
          type: number
          format: float
          nullable: true
        currency:
          $ref: '#/components/schemas/Currency'
        minimumSeats:
          type: integer
    GlobalPlanDefinition:
      type: object
      required:
        - planName
        - paymentPlan
        - featureFlags
      properties:
        planName:
          type: string
        paymentPlan:
          $ref: '#/components/schemas/PaymentPlan'
        featureFlags:
          type: array
          items:
            type: string
        pricing:
          $ref: '#/components/schemas/PlanPricing'
        revision:
          type: integer
          description: Assigned by the billing service on every change and ignored on a PUT body. 0 for a plan not changed since revision tracking started (it counts as revision 1).
    ComputerName:
      type: object
      properties:
        name:
          type: string
          description: Name of the computer
      required:
        - name
    Config:
      type: object
      properties:
        config_id:
          type: string
          description: ID of the phishing config
        organization_id:
          type: string
          description: ID of the organization
        send_response:
          type: boolean
          description: Whether to send a response to phishing attempts
        domains:
          type: array
          items:
            type: string
          description: List of domains for phishing config
        fwd_address:
          type: string
          description: Forward address for phishing emails
          nullable: true
        phishing_inbox_name:
          type: string
          description: Name of the phishing inbox
          nullable: true
      required:
        - config_id
        - organization_id
        - send_response
        - domains
    ConfigFields:
      type: object
      properties:
        send_response:
          type: boolean
          description: Whether to send a response to phishing attempts
        domains:
          type: array
          items:
            type: string
          description: List of domains for phishing config
        fwd_address:
          type: string
          description: Forward address for phishing emails
          nullable: true
        phishing_inbox_name:
          type: string
          description: Name of the phishing inbox
          nullable: true
      required:
        - send_response
        - domains
    ConfigsList:
      type: array
      items:
        $ref: '#/components/schemas/Config'
    DomainVerificationResult:
      type: object
      properties:
        organization_id:
          type: string
          description: ID of the organization
        domain:
          type: string
          description: Domain name
        domain_timestamp:
          type: string
          description: Domain timestamp
        timestamp:
          type: integer
          format: int64
          description: Unix timestamp
        config_id:
          type: string
          description: ID of the config
        dmarc:
          type: object
          properties:
            valid:
              type: boolean
              description: Whether DMARC record is valid
            record:
              type: string
              description: DMARC record
            error:
              type: string
              description: Error message if validation failed
            security_score:
              type: integer
              description: Security score for DMARC
            policy:
              type: string
              description: DMARC policy
            subdomain_policy:
              type: string
              description: Subdomain policy
            alignment:
              type: object
              properties:
                dkim:
                  type: string
                  description: 'DKIM alignment (strict, relaxed)'
                spf:
                  type: string
                  description: 'SPF alignment (strict, relaxed)'
              required:
                - dkim
                - spf
            reporting:
              type: object
              properties:
                aggregate_uri:
                  type: string
                  description: Aggregate reporting URI
                forensic_uri:
                  type: string
                  description: Forensic reporting URI
                percentage:
                  type: integer
                  description: Percentage
              required:
                - percentage
            recommendations:
              type: array
              items:
                type: string
              description: Recommendations for improvement
            warnings:
              type: array
              items:
                type: string
              description: Warnings
          required:
            - valid
            - security_score
            - alignment
            - reporting
        spf:
          type: object
          properties:
            valid:
              type: boolean
              description: Whether SPF record is valid
            record:
              type: string
              description: SPF record
            error:
              type: string
              description: Error message if validation failed
            security_score:
              type: integer
              description: Security score for SPF
            all_mechanism:
              type: string
              description: All mechanism
            lookup_count:
              type: integer
              description: Number of lookups
            has_ipv6:
              type: boolean
              description: Whether IPv6 is present
            record_length:
              type: integer
              description: Record length
            recommendations:
              type: array
              items:
                type: string
              description: Recommendations for improvement
            warnings:
              type: array
              items:
                type: string
              description: Warnings
          required:
            - valid
            - security_score
            - lookup_count
            - has_ipv6
            - record_length
        dkim:
          type: object
          properties:
            selectors:
              type: array
              items:
                type: object
                properties:
                  selector:
                    type: string
                    description: Selector name
                  found:
                    type: boolean
                    description: Whether selector was found
                  valid:
                    type: boolean
                    description: Whether selector is valid
                  record:
                    type: string
                    description: DKIM record
                  key_length:
                    type: integer
                    description: Key length
                  key_algorithm:
                    type: string
                    description: Key algorithm
                  hash_algorithm:
                    type: string
                    description: Hash algorithm
                  service_type:
                    type: string
                    description: Service type
                required:
                  - selector
                  - found
                  - valid
                  - key_length
              description: DKIM selectors
            security_score:
              type: integer
              description: Security score for DKIM
            recommendations:
              type: array
              items:
                type: string
              description: Recommendations for improvement
            warnings:
              type: array
              items:
                type: string
              description: Warnings
          required:
            - selectors
            - security_score
        dnssec:
          type: object
          properties:
            valid:
              type: boolean
              description: Whether DNSSEC is valid
            error:
              type: string
              description: Error message if validation failed
            security_score:
              type: integer
              description: Security score for DNSSEC
            algorithm:
              type: string
              description: Algorithm
            key_length:
              type: integer
              description: Key length
            chain_valid:
              type: boolean
              description: Whether chain is valid
            recommendations:
              type: array
              items:
                type: string
              description: Recommendations for improvement
            warnings:
              type: array
              items:
                type: string
              description: Warnings
          required:
            - valid
            - security_score
            - chain_valid
        overall_score:
          type: integer
          description: Overall security score
        ttl:
          type: integer
          format: int64
          description: Time to live
      required:
        - organization_id
        - domain
        - timestamp
        - config_id
        - dmarc
        - spf
        - dkim
        - dnssec
        - overall_score
        - ttl
    ConnectionError:
      type: object
      properties:
        GoogleMobileDevicsAPIError:
          type: string
          description: Google Mobile Devices API Error
        GoogleCloudIdentityAPIError:
          type: string
          description: Google Cloud Identity API Error
        GoogleChromeOSDevicesAPIError:
          type: string
          description: Google Chrome OS Devices API Error
        MicrosoftAPIError:
          type: string
          description: Microsoft API Error
    CVE:
      type: object
      properties:
        categories:
          type: array
          items:
            type: string
            enum:
              - Data Breach
              - Phishing
              - Ransomware
        cisaActionDue:
          type: string
        cisaExploitAdd:
          type: string
        cisaRequiredAction:
          type: string
        cisaVulnerabilityName:
          type: string
        configurations:
          type: array
          items:
            type: object
            properties:
              negate:
                type: boolean
              nodes:
                type: array
                items:
                  type: object
                  properties:
                    cpeMatch:
                      type: array
                      items:
                        type: object
                        properties:
                          criteria:
                            type: string
                          matchCriteriaId:
                            type: string
                          versionEndExcluding:
                            type: string
                          versionEndIncluding:
                            type: string
                          versionStartExcluding:
                            type: string
                          versionStartIncluding:
                            type: string
                          vulnerable:
                            type: boolean
                    negate:
                      type: boolean
                    operator:
                      type: string
              operator:
                type: string
        cveTags:
          type: array
          items:
            type: object
            properties:
              sourceIdentifier:
                type: string
              tags:
                type: array
                items:
                  type: string
        descriptions:
          type: array
          items:
            type: object
            properties:
              lang:
                type: string
              value:
                type: string
        evaluatorComment:
          type: string
        evaluatorImpact:
          type: string
        evaluatorSolution:
          type: string
        id:
          type: string
        kev:
          type: object
          properties:
            cveID:
              type: string
            cwes:
              type: array
              items:
                type: string
            dateAdded:
              type: string
            dueDate:
              type: string
            knownRansomwareCampaignUse:
              type: string
            notes:
              type: string
            product:
              type: string
            requiredAction:
              type: string
            shortDescription:
              type: string
            vendorProject:
              type: string
            vulnerabilityName:
              type: string
        lastModified:
          type: string
        metrics:
          type: object
          properties:
            cvssMetricV2:
              type: array
              items:
                type: object
                properties:
                  acInsufInfo:
                    type: boolean
                  baseSeverity:
                    type: string
                  cvssData:
                    type: object
                    properties:
                      accessComplexity:
                        type: string
                      accessVector:
                        type: string
                      authentication:
                        type: string
                      availabilityImpact:
                        type: string
                      baseScore:
                        type: number
                        format: float
                      confidentialityImpact:
                        type: string
                      integrityImpact:
                        type: string
                      vectorString:
                        type: string
                  exploitabilityScore:
                    type: number
                    format: float
                  impactScore:
                    type: number
                    format: float
                  obtainAllPrivilege:
                    type: boolean
                  obtainOtherPrivilege:
                    type: boolean
                  obtainUserPrivilege:
                    type: boolean
                  source:
                    type: string
                  type:
                    type: string
                  userInteractionRequired:
                    type: boolean
            cvssMetricV30:
              type: array
              items:
                type: object
                properties:
                  cvssData:
                    type: object
                    properties:
                      accessComplexity:
                        type: string
                      attackVector:
                        type: string
                      authentication:
                        type: string
                      availabilityImpact:
                        type: string
                      baseScore:
                        type: number
                        format: float
                      confidentialityImpact:
                        type: string
                      integrityImpact:
                        type: string
                      vectorString:
                        type: string
                  exploitabilityScore:
                    type: number
                    format: float
                  impactScore:
                    type: number
                    format: float
                  source:
                    type: string
                  type:
                    type: string
            cvssMetricV31:
              type: array
              items:
                type: object
                properties:
                  cvssData:
                    type: object
                    properties:
                      accessComplexity:
                        type: string
                      attackVector:
                        type: string
                      authentication:
                        type: string
                      availabilityImpact:
                        type: string
                      baseScore:
                        type: number
                        format: float
                      confidentialityImpact:
                        type: string
                      integrityImpact:
                        type: string
                      vectorString:
                        type: string
                  exploitabilityScore:
                    type: number
                    format: float
                  impactScore:
                    type: number
                    format: float
                  source:
                    type: string
                  type:
                    type: string
            cvssMetricV40:
              type: array
              items:
                type: object
                properties:
                  cvssData:
                    type: object
                    properties:
                      accessComplexity:
                        type: string
                      attackVector:
                        type: string
                      availabilityImpact:
                        type: string
                      baseScore:
                        type: number
                        format: float
                      confidentialityImpact:
                        type: string
                      exploitabilityScore:
                        type: number
                        format: float
                      impactScore:
                        type: number
                        format: float
                      integrityImpact:
                        type: string
                      privilegesRequired:
                        type: string
                      scope:
                        type: string
                      userInteraction:
                        type: string
                      vectorString:
                        type: string
                  source:
                    type: string
                  type:
                    type: string
        published:
          type: string
        references:
          type: array
          items:
            type: object
            properties:
              source:
                type: string
              tags:
                type: array
                items:
                  type: string
              url:
                type: string
        software_name:
          type: string
        sourceIdentifier:
          type: string
        tag:
          type: string
        vendorComments:
          type: array
          items:
            type: object
            properties:
              comment:
                type: string
              lastModified:
                type: string
              organization:
                type: string
        vulnStatus:
          type: string
        weaknesses:
          type: array
          items:
            type: object
            properties:
              description:
                type: array
                items:
                  type: object
                  properties:
                    lang:
                      type: string
                    value:
                      type: string
              source:
                type: string
              type:
                type: string
    DashboardUser:
      type: object
      properties:
        organization_id:
          type: string
          description: ID of the organization
        email:
          type: string
          description: Email of the user
        user_id:
          type: string
          description: ID of the user
        timestamp:
          type: string
          description: Timestamp of the user
        notifications_weekly_report:
          type: boolean
          description: Whether the user receives weekly report notifications
        notifications_email_reporting:
          type: boolean
          description: Whether the user receives email reporting notifications
        notifications_email_marketing:
          type: boolean
          description: Whether the user receives email marketing notifications
        notifications_email_product_updates:
          type: boolean
          description: Whether the user receives product updates notifications
        notifications_email_product_assistance:
          type: boolean
          description: Whether the user receives product assistance notifications
        notifications_admin_preview_device_risk:
          type: boolean
          description: Whether the user receives admin preview device risk notifications
        language:
          type: string
          description: User's preferred language
          enum:
            - en
            - nl
        suggested_tasks_state:
          type: string
          description: JSON-encoded map of suggested task states
        role_type:
          type: string
          description: Role type of the user
        referral_code:
          type: string
          description: 'The user''s own shareable referral code, generated on first read'
      required:
        - organization_id
        - email
        - user_id
        - timestamp
        - notifications_weekly_report
        - notifications_email_reporting
        - notifications_email_marketing
        - notifications_email_product_updates
        - notifications_email_product_assistance
        - notifications_admin_preview_device_risk
        - language
    DeleteDiscountCodeRequest:
      type: object
      properties:
        code:
          type: string
          description: The discount code to delete
      required:
        - code
    Decisions:
      type: object
      description: 'Policy decisions for the device, keyed by check. Every entry has a status except the browser entries (chrome, firefox, edge, safari, opera, brave, chromium, vivaldi, arc), which are BrowserDecision objects holding nested decisions and no status: consumers iterating over decisions must skip them or read their nested decisions.'
      properties:
        affiliated:
          $ref: '#/components/schemas/DecisionAffiliated'
        antivirus:
          $ref: '#/components/schemas/DecisionAntivirus'
        beta_browser_version:
          $ref: '#/components/schemas/DecisionEnabled'
        beta_os_version:
          $ref: '#/components/schemas/DecisionEnabled'
        browser_up_to_date:
          $ref: '#/components/schemas/DecisionVersion'
        disk_encryption:
          $ref: '#/components/schemas/DecisionEnabled'
        installed:
          $ref: '#/components/schemas/DecisionInstalled'
        mfa:
          $ref: '#/components/schemas/DecisionMfa'
        older_supported_browser_version:
          $ref: '#/components/schemas/DecisionEnabled'
        older_supported_os_version:
          $ref: '#/components/schemas/DecisionEnabled'
        os_autoupdate:
          $ref: '#/components/schemas/DecisionEnabled'
        os_up_to_date:
          $ref: '#/components/schemas/DecisionVersion'
        passwordmanager:
          $ref: '#/components/schemas/DecisionPasswordmanager'
        screenlock:
          $ref: '#/components/schemas/DecisionEnabled'
        skip:
          $ref: '#/components/schemas/DecisionSkip'
        unsupported:
          $ref: '#/components/schemas/DecisionUnsupported'
        biometrics:
          $ref: '#/components/schemas/DecisionBiometrics'
        firewall:
          $ref: '#/components/schemas/DecisionEnabled'
        screen_sharing:
          $ref: '#/components/schemas/DecisionEnabled'
        remote_login:
          $ref: '#/components/schemas/DecisionEnabled'
        remote_management:
          $ref: '#/components/schemas/DecisionEnabled'
        remote_scripting:
          $ref: '#/components/schemas/DecisionEnabled'
        unattended_remote_access:
          $ref: '#/components/schemas/DecisionEnabled'
        reboot:
          $ref: '#/components/schemas/DecisionReboot'
        windows_recall:
          $ref: '#/components/schemas/DecisionEnabled'
        xfa_version:
          $ref: '#/components/schemas/DecisionVersionInDays'
        dns:
          $ref: '#/components/schemas/DecisionDNS'
        aikido_safe_chain:
          $ref: '#/components/schemas/DecisionAikido'
        aikido_endpoint:
          $ref: '#/components/schemas/DecisionAikido'
        unsigned_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "Apps with no signature"'
        tampered_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "Tampered apps"'
        revoked_signature_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "Apps with a revoked certificate"'
        untrusted_publisher_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "Apps from an unknown developer"'
        unnotarized_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "Apps whose developer skipped Apple''s malware check"'
        adhoc_signed_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "Self-signed apps"'
        cryptominer_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "Crypto-mining apps"'
        hacking_tool_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "Hacking & security-testing tools"'
        jailbreak_tool_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "Device-restriction removal tools"'
        piracy_p2p_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "File-sharing & pirated-content apps"'
        third_party_ai_coding_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "Third-party AI coding assistants"'
        experimental_browser_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "Lesser-known web browsers"'
        game_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "Games & gaming apps"'
        permission_hungry_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "Apps requesting broad permissions"'
        virtualization_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "Virtual machine software"'
        vpn_client_applications:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "VPN apps"'
        install_protection:
          allOf:
            - $ref: '#/components/schemas/DecisionEnabled'
          description: 'Application check, shown in the XFA app as "App installation safety check"'
        jailbroken:
          $ref: '#/components/schemas/DecisionEnabled'
        rooted:
          $ref: '#/components/schemas/DecisionEnabled'
        developer_mode:
          $ref: '#/components/schemas/DecisionEnabled'
        find_my_device:
          $ref: '#/components/schemas/DecisionEnabled'
        secure_boot:
          $ref: '#/components/schemas/DecisionEnabled'
        integrity_protection:
          $ref: '#/components/schemas/DecisionEnabled'
        vanta:
          $ref: '#/components/schemas/DecisionEnabled'
        secrets_in_environment:
          $ref: '#/components/schemas/DecisionEnabled'
        autonomous_agents_present:
          $ref: '#/components/schemas/DecisionEnabled'
        unguarded_elevation:
          $ref: '#/components/schemas/DecisionEnabled'
        unsafe_ai_mode:
          $ref: '#/components/schemas/DecisionEnabled'
        chrome_safebrowsing_enabled:
          $ref: '#/components/schemas/DecisionEnabled'
        chrome_safebrowsing_enhanced:
          $ref: '#/components/schemas/DecisionEnabled'
        chrome_do_not_track:
          $ref: '#/components/schemas/DecisionEnabled'
        chrome_dns_over_https:
          $ref: '#/components/schemas/DecisionEnabled'
        firefox_https_only:
          $ref: '#/components/schemas/DecisionEnabled'
        firefox_dns_over_https:
          $ref: '#/components/schemas/DecisionEnabled'
        firefox_enhanced_tracking_protection:
          $ref: '#/components/schemas/DecisionEnabled'
        firefox_enhanced_tracking_protection_strict:
          $ref: '#/components/schemas/DecisionEnabled'
        intune:
          $ref: '#/components/schemas/DecisionIntune'
        chrome:
          $ref: '#/components/schemas/BrowserDecision'
        firefox:
          $ref: '#/components/schemas/BrowserDecision'
        edge:
          $ref: '#/components/schemas/BrowserDecision'
        safari:
          $ref: '#/components/schemas/BrowserDecision'
        opera:
          $ref: '#/components/schemas/BrowserDecision'
        brave:
          $ref: '#/components/schemas/BrowserDecision'
        chromium:
          $ref: '#/components/schemas/BrowserDecision'
        vivaldi:
          $ref: '#/components/schemas/BrowserDecision'
        arc:
          $ref: '#/components/schemas/BrowserDecision'
    DecisionAffiliated:
      type: object
      properties:
        status:
          type: string
      required:
        - status
    DecisionAikido:
      type: object
      description: Decision for Aikido device checks (Safe Chain or Endpoint). Combines presence + version posture under a single status.
      properties:
        first_seen_at:
          type: string
          description: 'First failing sign-in on this device, as RFC3339 UTC. This one-time date never resets.'
        block_at:
          type: string
          description: RFC3339 UTC deadline for a one-time grace period.
        reason:
          $ref: '#/components/schemas/DecisionReason'
        status:
          type: string
          enum:
            - OK
            - WARNING
            - BLOCKING
          description: Status of the decision (OK / WARNING / BLOCKING)
        installed:
          type: boolean
          description: Whether the Aikido product is installed on the device
        active:
          type: boolean
          description: Whether the Aikido product is active (Safe Chain shell integration on PATH; Endpoint system extension running)
        version:
          type: string
          description: Installed version on the device
        latest_version:
          type: string
          description: Latest known version (from xfa-versions-service)
        up_to_date:
          type: boolean
          description: Whether the installed version matches the latest known version
        fix_supported:
          type: boolean
          description: 'Whether the XFA app on this device can fix this check itself, after the person clicks and confirms. Absent when the policy engine does not report it.'
        enabled:
          type: boolean
          description: Is the check enabled?
        enforced:
          type: boolean
          description: 'Whether this check is enforced towards the user: the policy warns and/or blocks on it. False means the policy only tracks a compliance goal, which is dashboard-only, so clients must not present the check to the user as passed or failed. Absent when enforcement could not be determined; treat absent as enforced.'
        goal_status:
          $ref: '#/components/schemas/GoalStatus'
        covered_by:
          type: string
          description: 'Set when the check passes because another check covers it, naming that check''s key. Today only aikido_safe_chain, covered by aikido_endpoint. Absent when the check passes on its own.'
        endpoint_token:
          type: string
          description: 'Aikido Endpoint registration token, used by the XFA app for one-click self-installation and tenant association. Only on aikido_endpoint, and only when a token is set on the policy.'
      required:
        - status
    DecisionBiometrics:
      type: object
      properties:
        first_seen_at:
          type: string
          description: 'First failing sign-in on this device, as RFC3339 UTC. This one-time date never resets.'
        block_at:
          type: string
          description: RFC3339 UTC deadline for a one-time grace period.
        reason:
          $ref: '#/components/schemas/DecisionReason'
        status:
          type: string
          enum:
            - OK
            - WARNING
            - BLOCKING
          description: status of decision
        fix_supported:
          type: boolean
          description: 'Whether the XFA app on this device can fix this check itself, after the person clicks and confirms. Absent when the policy engine does not report it.'
        enabled:
          type: boolean
          description: Is the check enabled?
        enforced:
          type: boolean
          description: 'Whether this check is enforced towards the user: the policy warns and/or blocks on it. False means the policy only tracks a compliance goal, which is dashboard-only, so clients must not present the check to the user as passed or failed. Absent when enforcement could not be determined; treat absent as enforced.'
        goal_status:
          $ref: '#/components/schemas/GoalStatus'
        covered_by:
          type: string
          description: 'Set when the check passes because another check covers it, naming that check''s key. Today only aikido_safe_chain, covered by aikido_endpoint. Absent when the check passes on its own.'
      required:
        - status
    DecisionReason:
      type: string
      enum:
        - not_shared
        - no_permission
        - not_configured
      description: 'Why a decision has no device value. not_shared: the person does not share this check with the organization (affiliation sharing); status is the policy''s severity (BLOCKING, WARNING, or OK for a goal-only check). Only not_shared is used today; the others are reserved (XFA-3686). Absent on a normal decision.'
      example: not_shared
    DecisionEnabled:
      type: object
      properties:
        first_seen_at:
          type: string
          description: 'First failing sign-in on this device, as RFC3339 UTC. This one-time date never resets.'
        block_at:
          type: string
          description: RFC3339 UTC deadline for a one-time grace period.
        reason:
          $ref: '#/components/schemas/DecisionReason'
        status:
          type: string
        fix_supported:
          type: boolean
          description: 'Whether the XFA app on this device can fix this check itself, after the person clicks and confirms. Absent when the policy engine does not report it.'
        enabled:
          type: boolean
          description: Is the check enabled?
        enforced:
          type: boolean
          description: 'Whether this check is enforced towards the user: the policy warns and/or blocks on it. False means the policy only tracks a compliance goal, which is dashboard-only, so clients must not present the check to the user as passed or failed. Absent when enforcement could not be determined; treat absent as enforced.'
        goal_status:
          $ref: '#/components/schemas/GoalStatus'
        covered_by:
          type: string
          description: 'Set when the check passes because another check covers it, naming that check''s key. Today only aikido_safe_chain, covered by aikido_endpoint. Absent when the check passes on its own.'
      required:
        - status
    DecisionInstalled:
      type: object
      properties:
        status:
          type: string
      required:
        - status
    DecisionMfa:
      type: object
      properties:
        autoApprove:
          type: boolean
        autoApproved:
          type: boolean
        credentials:
          type: object
          properties:
            credentials:
              type: array
              items:
                type: object
                properties:
                  deviceId:
                    type: string
                  id:
                    type: string
            displayName:
              type: string
            id:
              type: string
            name:
              type: string
            userId:
              type: string
        error:
          type: string
        status:
          type: string
      required:
        - status
    DecisionPasswordmanager:
      type: object
      properties:
        first_seen_at:
          type: string
          description: 'First failing sign-in on this device, as RFC3339 UTC. This one-time date never resets.'
        block_at:
          type: string
          description: RFC3339 UTC deadline for a one-time grace period.
        status:
          type: string
        fix_supported:
          type: boolean
          description: 'Whether the XFA app on this device can fix this check itself, after the person clicks and confirms. Absent when the policy engine does not report it.'
        enforced:
          type: boolean
          description: 'Whether this check is enforced towards the user: the policy warns and/or blocks on it. False means the policy only tracks a compliance goal, which is dashboard-only, so clients must not present the check to the user as passed or failed. Absent when enforcement could not be determined; treat absent as enforced.'
        goal_status:
          $ref: '#/components/schemas/GoalStatus'
      required:
        - status
    DecisionSkip:
      type: object
      properties:
        limit:
          type: integer
          minimum: 1
        remaining:
          type: integer
          minimum: 0
        allowed:
          type: boolean
      required:
        - allowed
    DecisionUnsupported:
      type: object
      properties:
        allowed:
          type: boolean
      required:
        - allowed
    DecisionVersion:
      type: object
      properties:
        status:
          type: string
        latest_version:
          type: string
        time_since_outdated:
          type: integer
        time_till_blocked:
          type: integer
        fix_supported:
          type: boolean
          description: 'Whether the XFA app on this device can fix this check itself, after the person clicks and confirms. Absent when the policy engine does not report it.'
        enforced:
          type: boolean
          description: 'Whether this check is enforced towards the user: the policy warns and/or blocks on it. False means the policy only tracks a compliance goal, which is dashboard-only, so clients must not present the check to the user as passed or failed. Absent when enforcement could not be determined; treat absent as enforced.'
        goal_status:
          $ref: '#/components/schemas/GoalStatus'
      required:
        - status
        - latest_version
        - time_since_outdated
    DecisionVersionInDays:
      type: object
      properties:
        status:
          type: string
          enum:
            - OK
            - WARNING
            - BLOCKING
          description: status of decision
        latest_version:
          type: string
          description: the latest version
        time_since_outdated:
          type: integer
        days_till_blocked:
          type: integer
        days_since_blocked:
          type: integer
        fix_supported:
          type: boolean
          description: 'Whether the XFA app on this device can fix this check itself, after the person clicks and confirms. Absent when the policy engine does not report it.'
        enforced:
          type: boolean
          description: 'Whether this check is enforced towards the user: the policy warns and/or blocks on it. False means the policy only tracks a compliance goal, which is dashboard-only, so clients must not present the check to the user as passed or failed. Absent when enforcement could not be determined; treat absent as enforced.'
        goal_status:
          $ref: '#/components/schemas/GoalStatus'
      required:
        - status
        - latest_version
        - time_since_outdated
    DecisionReboot:
      type: object
      properties:
        status:
          type: string
          enum:
            - OK
            - WARNING
            - BLOCKING
          description: status of decision
        time_since_last_reboot:
          type: integer
        time_till_blocked:
          type: integer
        time_since_blocked:
          type: integer
        fix_supported:
          type: boolean
          description: 'Whether the XFA app on this device can fix this check itself, after the person clicks and confirms. Absent when the policy engine does not report it.'
        enforced:
          type: boolean
          description: 'Whether this check is enforced towards the user: the policy warns and/or blocks on it. False means the policy only tracks a compliance goal, which is dashboard-only, so clients must not present the check to the user as passed or failed. Absent when enforcement could not be determined; treat absent as enforced.'
        goal_status:
          $ref: '#/components/schemas/GoalStatus'
      required:
        - status
        - time_since_last_reboot
    DecisionAntivirus:
      type: object
      description: 'Antivirus decision: which required antivirus product was found, or why the check fails.'
      properties:
        first_seen_at:
          type: string
          description: 'First failing sign-in on this device, as RFC3339 UTC. This one-time date never resets.'
        block_at:
          type: string
          description: RFC3339 UTC deadline for a one-time grace period.
        status:
          type: string
        fix_supported:
          type: boolean
          description: 'Whether the XFA app on this device can fix this check itself, after the person clicks and confirms. Absent when the policy engine does not report it.'
        enforced:
          type: boolean
          description: 'Whether this check is enforced towards the user: the policy warns and/or blocks on it. False means the policy only tracks a compliance goal, which is dashboard-only, so clients must not present the check to the user as passed or failed. Absent when enforcement could not be determined; treat absent as enforced.'
        goal_status:
          $ref: '#/components/schemas/GoalStatus'
        enabled:
          type: boolean
          description: Is the check enabled?
        reason:
          type: string
          enum:
            - product_missing
            - product_inactive
            - definitions_outdated
            - status_unknown
            - client_update_required
            - inventory_unavailable
          description: Why the check does not pass. Absent when it passes.
        required_products:
          type: array
          items:
            type: string
          description: Antivirus products the policy accepts
        matched_product_id:
          type: string
          description: The accepted antivirus product found on the device
      required:
        - status
    DecisionDNS:
      type: object
      properties:
        first_seen_at:
          type: string
          description: 'First failing sign-in on this device, as RFC3339 UTC. This one-time date never resets.'
        block_at:
          type: string
          description: RFC3339 UTC deadline for a one-time grace period.
        status:
          type: string
        fix_supported:
          type: boolean
          description: 'Whether the XFA app on this device can fix this check itself, after the person clicks and confirms. Absent when the policy engine does not report it.'
        enforced:
          type: boolean
          description: 'Whether this check is enforced towards the user: the policy warns and/or blocks on it. False means the policy only tracks a compliance goal, which is dashboard-only, so clients must not present the check to the user as passed or failed. Absent when enforcement could not be determined; treat absent as enforced.'
        goal_status:
          $ref: '#/components/schemas/GoalStatus'
        dnsServers:
          type: array
          nullable: true
          items:
            type: string
          description: List of DNS servers. Can be null when the statistics service has none.
          example:
            - 8.8.8.8
            - 1.1.1.1
        validationMode:
          $ref: '#/components/schemas/DNSValidationMode'
        requiredDnsServers:
          type: array
          nullable: true
          items:
            type: string
          description: List of required DNS servers. Can be null when the statistics service has none.
          example:
            - 8.8.8.8
            - 1.1.1.1
      required:
        - status
    DecisionIntune:
      type: object
      properties:
        first_seen_at:
          type: string
          description: 'First failing sign-in on this device, as RFC3339 UTC. This one-time date never resets.'
        block_at:
          type: string
          description: RFC3339 UTC deadline for a one-time grace period.
        status:
          type: string
        fix_supported:
          type: boolean
          description: 'Whether the XFA app on this device can fix this check itself, after the person clicks and confirms. Absent when the policy engine does not report it.'
        enforced:
          type: boolean
          description: 'Whether this check is enforced towards the user: the policy warns and/or blocks on it. False means the policy only tracks a compliance goal, which is dashboard-only, so clients must not present the check to the user as passed or failed. Absent when enforcement could not be determined; treat absent as enforced.'
        goal_status:
          $ref: '#/components/schemas/GoalStatus'
        enabled:
          type: boolean
          description: Is the check enabled?
        enrolled_in_external_tenant:
          type: boolean
          description: Whether the device is enrolled in an external tenant (not in the policy's tenant ID list)
      required:
        - status
    BrowserDecision:
      type: object
      description: 'Per-browser decisions for one installed browser. Unlike every other decision, a browser entry has no status of its own: it is a nested object holding the browser''s own decisions. Consumers iterating over decisions must skip browser entries (or read their nested decisions) instead of reading status.'
      properties:
        browser_name:
          type: string
        up_to_date:
          $ref: '#/components/schemas/DecisionVersion'
        beta_version:
          $ref: '#/components/schemas/DecisionEnabled'
        older_supported_version:
          $ref: '#/components/schemas/DecisionEnabled'
      required:
        - browser_name
    GoalStatus:
      type: string
      enum:
        - OK
        - NOK
        - UNKNOWN
        - NOT_REQUIRED
        - ''
      description: 'Goal status of the decision, based on the policy''s compliance goal and goal time. An empty string means the statistics service did not set it.'
      example: OK
    DNSValidationMode:
      type: string
      enum:
        - exact_match
        - exact_with_extra
        - contains
        - ''
      description: DNS validation mode. An empty string means the statistics service did not set it.
    Device:
      type: object
      properties:
        admin_mfa_approval_status:
          type: string
          enum:
            - PENDING
            - APPROVED
            - REJECTED
          description: Coarse administrator MFA approval badge visible only to Administrators.
        device_id:
          type: string
          description: ID of the device
        timestamp_submitted:
          type: integer
          description: Timestamp when the device was submitted (max of verified and discovery)
        timestamp_submitted_verified:
          type: integer
          description: Timestamp when the device was last submitted by the XFA agent (verified device)
        timestamp_submitted_discovery:
          type: integer
          description: 'Timestamp when the device was last submitted by a discovery provider (Microsoft, Google, Okta, etc.)'
        user:
          $ref: '#/components/schemas/User'
        computer_name:
          $ref: '#/components/schemas/ComputerName'
        battery:
          type: object
          properties:
            cycle_count:
              type: integer
              description: Battery cycle count
            health:
              type: string
              description: Battery health status
            max_capacity:
              type: number
              format: float
              description: Maximum battery capacity as a percentage
        os_name:
          type: string
          description: Name of the operating system
        os_version:
          type: string
          description: Version of the operating system
        os_build_number:
          type: string
          description: Build number of the operating system (e.g. for iOS)
        os_flavour:
          type: string
          description: Flavour of the operating system
        os_is_lts:
          type: boolean
          description: Whether the operating system is a long-term-support release (Ubuntu LTS / ESM)
        os_uptodate:
          type: boolean
          description: Whether the operating system is up to date
        os_outdated:
          type: integer
          description: Days OS is outdated
        os_rolling_release_last_full_update:
          type: integer
          format: int64
          description: 'Timestamp of the last full system update on a rolling-release distro (e.g. pacman -Syu on Arch Linux). Rolling releases are evaluated on update recency + local CVE audit rather than a version number, so os_version is not meaningful (it is typically "rolling").'
        os_rolling_release_has_security_risks_local_detection:
          type: boolean
          description: Whether a local security audit tool (e.g. arch-audit) detected known package vulnerabilities on a rolling-release distro. Basis for the OS up-to-date decision on rolling releases.
        os_evaluated_by_policy:
          type: boolean
          description: Whether the operating system is evaluated by policy
        os_autoupdate:
          type: boolean
          description: Whether the operating system auto-updates
        os_autoupdate_evaluated_by_policy:
          type: boolean
          description: Whether the operating system auto-update is evaluated by policy
        android_security_level:
          type: string
          description: Android security level
        manufacturer:
          type: string
          description: Manufacturer of the device
        model:
          type: string
          description: Model of the device
        model_identifier:
          type: string
          description: Identifier of the device model
        browser_last_used:
          type: string
          enum:
            - Chrome
            - Chromium
            - Firefox
            - Safari
            - Edge
            - Brave
            - Opera
            - Vivaldi
            - IE
            - Arc
          description: Name of the browser last used
        browser_uptodate:
          type: boolean
          description: Whether the browser is up to date
        browser_evaluated_by_policy:
          type: boolean
          description: Whether the browser is evaluated by policy
        chrome_version:
          type: string
          description: Version of Chrome browser
        chrome_uptodate:
          type: boolean
          description: Whether Chrome is up to date
        chrome_outdated:
          type: integer
          description: Days Chrome is outdated
        chrome_safebrowsing_enabled:
          type: boolean
          description: Whether Chrome Safe Browsing is enabled
        chrome_safebrowsing_evaluated_by_policy:
          type: boolean
          description: Whether Chrome Safe Browsing is evaluated by policy
        chrome_safebrowsing_enhanced:
          type: boolean
          description: Whether Chrome Safe Browsing Enhanced is enabled
        chrome_safebrowsing_enhanced_evaluated_by_policy:
          type: boolean
          description: Whether Chrome Safe Browsing Enhanced is evaluated by policy
        chrome_do_not_track:
          type: boolean
          description: Whether Chrome Do Not Track is enabled
        chrome_do_not_track_evaluated_by_policy:
          type: boolean
          description: Whether Chrome Do Not Track is evaluated by policy
        chrome_dns_over_https:
          type: boolean
          description: Whether Chrome DNS over HTTPS is enabled
        chrome_dns_over_https_evaluated_by_policy:
          type: boolean
          description: Whether Chrome DNS over HTTPS is evaluated by policy
        firefox_version:
          type: string
          description: Version of Firefox browser
        firefox_uptodate:
          type: boolean
          description: Whether Firefox is up to date
        firefox_outdated:
          type: integer
          description: Days Firefox is outdated
        firefox_https_only:
          type: boolean
          description: Whether Firefox HTTPS Only mode is enabled
        firefox_https_only_evaluated_by_policy:
          type: boolean
          description: Whether Firefox HTTPS Only mode is evaluated by policy
        firefox_dns_over_https:
          type: boolean
          description: Whether Firefox DNS over HTTPS is enabled
        firefox_dns_over_https_evaluated_by_policy:
          type: boolean
          description: Whether Firefox DNS over HTTPS is evaluated by policy
        firefox_enhanced_tracking_protection:
          type: boolean
          description: Whether Firefox Enhanced Tracking Protection is enabled
        firefox_enhanced_tracking_protection_evaluated_by_policy:
          type: boolean
          description: Whether Firefox Enhanced Tracking Protection is evaluated by policy
        firefox_enhanced_tracking_protection_strict:
          type: boolean
          description: Whether Firefox Enhanced Tracking Protection Strict mode is enabled
        firefox_enhanced_tracking_protection_strict_evaluated_by_policy:
          type: boolean
          description: Whether Firefox Enhanced Tracking Protection Strict mode is evaluated by policy
        edge_version:
          type: string
          description: Version of Edge browser
        edge_uptodate:
          type: boolean
          description: Whether Edge is up to date
        edge_outdated:
          type: integer
          description: Days Edge is outdated
        safari_version:
          type: string
          description: Version of Safari browser
        safari_uptodate:
          type: boolean
          description: Whether Safari is up to date
        safari_outdated:
          type: integer
          description: Days Safari is outdated
        brave_version:
          type: string
          description: Version of Brave browser
        brave_uptodate:
          type: boolean
          description: Whether Brave is up to date
        brave_outdated:
          type: integer
          description: Days Brave is outdated
        arc_version:
          type: string
          description: Version of Arc browser
        arc_uptodate:
          type: boolean
          description: Whether Arc is up to date
        arc_outdated:
          type: integer
          description: Days Arc is outdated
        opera_version:
          type: string
          description: Version of Opera browser
        opera_uptodate:
          type: boolean
          description: Whether Opera is up to date
        opera_outdated:
          type: integer
          description: Days Opera is outdated
        vivaldi_version:
          type: string
          description: Version of Vivaldi browser
        vivaldi_uptodate:
          type: boolean
          description: Whether Vivaldi is up to date
        vivaldi_outdated:
          type: integer
          description: Days Vivaldi is outdated
        diskencryption_supported:
          type: boolean
          description: Whether disk encryption is supported
        diskencryption_active:
          type: boolean
          description: Whether disk encryption is active
        diskencryption_evaluated_by_policy:
          type: boolean
          description: Whether disk encryption is evaluated by policy
        antivirus_enabled:
          type: boolean
          description: Whether antivirus is enabled
        antivirus_product_name:
          type: string
          description: Name of the detected antivirus product
        antivirus_installed:
          type: boolean
          description: Whether the antivirus product is installed
        antivirus_running:
          type: boolean
          description: Whether the antivirus product is running
        antivirus_uptodate:
          type: boolean
          description: Whether the antivirus definitions are up to date
        antivirus_inventory_status:
          type: string
          enum:
            - complete
            - partial
            - unavailable
          description: Completeness of the latest native antivirus measurement.
        antivirus_products:
          type: array
          maxItems: 32
          items:
            $ref: '#/components/schemas/AntivirusProduct'
        antivirus_timestamp:
          type: integer
          format: int64
          description: Server timestamp of the antivirus measurement; unrelated device updates do not refresh it.
        antivirus_source:
          type: string
          enum:
            - xfa_agent
            - browser
            - chrome_device_trust
            - edge_device_trust
            - discovery
          description: Server-assigned source of the antivirus measurement.
        antivirus_evaluated_by_policy:
          type: boolean
          description: Whether antivirus is evaluated by policy
        firewall_enabled:
          type: boolean
          description: Whether firewall is enabled
        firewall_evaluated_by_policy:
          type: boolean
          description: Whether firewall is evaluated by policy
        find_my_device_enabled:
          type: boolean
          description: Whether Find My Device is enabled
        find_my_device_evaluated_by_policy:
          type: boolean
          description: Whether Find My Device is evaluated by policy
        vanta_client_running:
          type: boolean
          description: Whether Vanta client is running
        vanta_client_running_evaluated_by_policy:
          type: boolean
          description: Whether Vanta client running is evaluated by policy
        aikido_safe_chain_supported:
          type: boolean
          description: 'Whether Aikido Safe Chain is supported on this device''s OS (cross-platform: mac/linux/windows)'
        aikido_safe_chain_installed:
          type: boolean
          description: Whether Aikido Safe Chain is installed on the device
        aikido_safe_chain_active:
          type: boolean
          description: Whether Aikido Safe Chain shell-profile integration is active (the wrapper is on PATH and intercepts package-manager calls)
        aikido_safe_chain_version:
          type: string
          description: Installed version of Aikido Safe Chain (from `safe-chain --version`)
        aikido_safe_chain_latest_version:
          type: string
          description: Latest known Aikido Safe Chain version (from xfa-versions-service)
        aikido_safe_chain_uptodate:
          type: boolean
          description: Whether the installed Aikido Safe Chain version matches the latest known version
        aikido_safe_chain_evaluated_by_policy:
          type: boolean
          description: Whether Aikido Safe Chain is evaluated by policy
        aikido_endpoint_supported:
          type: boolean
          description: Whether Aikido Endpoint is supported on this device's OS (macOS only today)
        aikido_endpoint_installed:
          type: boolean
          description: Whether the Aikido Endpoint agent is installed on the device
        aikido_endpoint_active:
          type: boolean
          description: Whether the Aikido Endpoint system extension is active
        aikido_endpoint_version:
          type: string
          description: Installed version of Aikido Endpoint (from the bundle's Info.plist)
        aikido_endpoint_latest_version:
          type: string
          description: Latest known Aikido Endpoint version (from xfa-versions-service)
        aikido_endpoint_uptodate:
          type: boolean
          description: Whether the installed Aikido Endpoint version matches the latest known version
        aikido_endpoint_evaluated_by_policy:
          type: boolean
          description: Whether Aikido Endpoint is evaluated by policy
        intune_enrolled:
          type: boolean
          description: Whether the device is enrolled in Intune
        intune_tenant_ids:
          type: array
          items:
            type: string
          description: List of Intune tenant IDs
        intune_evaluated_by_policy:
          type: boolean
          description: Whether Intune enrollment is evaluated by policy
        sentinelone_installed:
          type: boolean
          description: Whether the SentinelOne EDR agent is installed on the device
        sentinelone_management_url:
          type: string
          description: URL of the SentinelOne management console
        sentinelone_site_name:
          type: string
          description: Site name in the SentinelOne management console
        sentinelone_evaluated_by_policy:
          type: boolean
          description: Whether SentinelOne installation is evaluated by policy
        time_since_boot_in_days:
          type: integer
          description: 'Time since the device was last booted, in days'
        microsoft_word_version:
          type: string
          description: Version of Microsoft Word
        microsoft_word_uptodate:
          type: boolean
          description: Whether Microsoft Word is up to date
        microsoft_word_evaluated_by_policy:
          type: boolean
          description: Whether Microsoft Word is evaluated by policy
        microsoft_excel_version:
          type: string
          description: Version of Microsoft Excel
        microsoft_excel_uptodate:
          type: boolean
          description: Whether Microsoft Excel is up to date
        microsoft_excel_evaluated_by_policy:
          type: boolean
          description: Whether Microsoft Excel is evaluated by policy
        microsoft_powerpoint_version:
          type: string
          description: Version of Microsoft PowerPoint
        microsoft_powerpoint_uptodate:
          type: boolean
          description: Whether Microsoft PowerPoint is up to date
        microsoft_powerpoint_evaluated_by_policy:
          type: boolean
          description: Whether Microsoft PowerPoint is evaluated by policy
        microsoft_outlook_version:
          type: string
          description: Version of Microsoft Outlook
        microsoft_outlook_uptodate:
          type: boolean
          description: Whether Microsoft Outlook is up to date
        microsoft_outlook_evaluated_by_policy:
          type: boolean
          description: Whether Microsoft Outlook is evaluated by policy
        microsoft_teams_version:
          type: string
          description: Version of Microsoft Teams
        microsoft_teams_uptodate:
          type: boolean
          description: Whether Microsoft Teams is up to date
        microsoft_teams_evaluated_by_policy:
          type: boolean
          description: Whether Microsoft Teams is evaluated by policy
        slack_version:
          type: string
          description: Version of Slack
        slack_uptodate:
          type: boolean
          description: Whether Slack is up to date
        slack_evaluated_by_policy:
          type: boolean
          description: Whether Slack is evaluated by policy
        zoom_version:
          type: string
          description: Version of Zoom
        zoom_uptodate:
          type: boolean
          description: Whether Zoom is up to date
        zoom_evaluated_by_policy:
          type: boolean
          description: Whether Zoom is evaluated by policy
        skype_version:
          type: string
          description: Version of Skype
        skype_uptodate:
          type: boolean
          description: Whether Skype is up to date
        skype_evaluated_by_policy:
          type: boolean
          description: Whether Skype is evaluated by policy
        adobe_acrobat_reader_version:
          type: string
          description: Version of Adobe Acrobat Reader
        adobe_acrobat_reader_uptodate:
          type: boolean
          description: Whether Adobe Acrobat Reader is up to date
        adobe_acrobat_reader_evaluated_by_policy:
          type: boolean
          description: Whether Adobe Acrobat Reader is evaluated by policy
        adobe_acrobat_standard_or_pro_version:
          type: string
          description: Version of Adobe Acrobat Standard or Pro
        adobe_acrobat_standard_or_pro_uptodate:
          type: boolean
          description: Whether Adobe Acrobat Standard or Pro is up to date
        adobe_acrobat_standard_or_pro_evaluated_by_policy:
          type: boolean
          description: Whether Adobe Acrobat Standard or Pro is evaluated by policy
        foxit_reader_version:
          type: string
          description: Version of Foxit Reader
        foxit_reader_uptodate:
          type: boolean
          description: Whether Foxit Reader is up to date
        foxit_reader_evaluated_by_policy:
          type: boolean
          description: Whether Foxit Reader is evaluated by policy
        sumatra_pdf_version:
          type: string
          description: Version of Sumatra PDF
        sumatra_pdf_uptodate:
          type: boolean
          description: Whether Sumatra PDF is up to date
        sumatra_pdf_evaluated_by_policy:
          type: boolean
          description: Whether Sumatra PDF is evaluated by policy
        nitro_pdf_reader_version:
          type: string
          description: Version of Nitro PDF Reader
        nitro_pdf_reader_uptodate:
          type: boolean
          description: Whether Nitro PDF Reader is up to date
        nitro_pdf_reader_evaluated_by_policy:
          type: boolean
          description: Whether Nitro PDF Reader is evaluated by policy
        jailbroken:
          type: boolean
          description: Whether the device is jailbroken
        jailbroken_evaluated_by_policy:
          type: boolean
          description: Whether the device being jailbroken is evaluated by policy
        rooted:
          type: boolean
          description: Whether the device is rooted
        rooted_evaluated_by_policy:
          type: boolean
          description: Whether the device being rooted is evaluated by policy
        developer_mode:
          type: boolean
          description: Whether developer mode is enabled
        developer_mode_evaluated_by_policy:
          type: boolean
          description: Whether developer mode is evaluated by policy
        secure_boot_enabled:
          type: boolean
          description: Whether secure boot is enabled
        secure_boot_enabled_evaluated_by_policy:
          type: boolean
          description: Whether secure boot is evaluated by policy
        secure_boot_status:
          $ref: '#/components/schemas/SecurityStatus'
          description: Secure boot status
        remote_login_enabled:
          type: boolean
          description: Whether remote login is enabled
        remote_login_enabled_evaluated_by_policy:
          type: boolean
          description: Whether remote login is evaluated by policy
        remote_management_enabled:
          type: boolean
          description: Whether remote management is enabled
        remote_management_enabled_evaluated_by_policy:
          type: boolean
          description: Whether remote management is evaluated by policy
        screen_sharing_enabled:
          type: boolean
          description: Whether screen sharing is enabled
        screen_sharing_enabled_evaluated_by_policy:
          type: boolean
          description: Whether screen sharing is evaluated by policy
        remote_scripting_enabled:
          type: boolean
          description: Whether remote scripting is enabled
        remote_scripting_enabled_evaluated_by_policy:
          type: boolean
          description: Whether remote scripting is evaluated by policy
        unattended_remote_access_enabled:
          type: boolean
          description: Whether unattended remote access is enabled
        unattended_remote_access_enabled_evaluated_by_policy:
          type: boolean
          description: Whether unattended remote access is evaluated by policy
        integrity_protection_enabled:
          type: boolean
          description: Whether integrity protection is enabled
        integrity_protection_enabled_evaluated_by_policy:
          type: boolean
          description: Whether integrity protection is evaluated by policy
        integrity_protection_status:
          description: Integrity protection status
          type: string
          enum:
            - supported
            - active
            - inactive
            - unknown
        dns_servers_evaluated_by_policy:
          type: boolean
          description: Whether DNS servers are evaluated by policy
        dns_servers_compliant:
          type: boolean
          description: Whether DNS servers are compliant
        dns_validation_mode:
          description: DNS validation mode
          type: string
          enum:
            - exact_match
            - exact_with_extra
            - contains
        dns_status:
          $ref: '#/components/schemas/SecurityStatus'
          description: DNS status
        has_recently_rebooted:
          type: boolean
          description: Whether device has recently rebooted
        has_recently_rebooted_evaluated_by_policy:
          type: boolean
          description: Whether recent reboot is evaluated by policy
        windows_recall:
          type: object
          properties:
            active:
              type: boolean
              description: Whether Windows Recall is active
            available:
              type: boolean
              description: Whether Windows Recall is available
          description: Windows Recall information
        windows_recall_evaluated_by_policy:
          type: boolean
          description: Whether Windows Recall is evaluated by policy
        xfa_version_evaluated_by_policy:
          type: boolean
          description: Whether XFA version is evaluated by policy
        xfa_up_to_date:
          type: boolean
          description: Whether XFA is up to date
        xfa_outdated:
          type: integer
          description: Days XFA is outdated
        passwordmanager:
          $ref: '#/components/schemas/PasswordManager'
        passwordmanager_evaluated_by_policy:
          type: boolean
          description: Whether password manager is evaluated by policy
        nativeclient_installed:
          type: boolean
          description: Whether native client is installed
        nativeclient_evaluated_by_policy:
          type: boolean
          description: Whether native client installation is evaluated by policy
        authentication_active:
          type: boolean
          description: Whether authentication is active
        authentication_evaluated_by_policy:
          type: boolean
          description: Whether authentication is evaluated by policy
        biometrics:
          type: string
          description: Biometrics information
        biometrics_evaluated_by_policy:
          type: boolean
          description: Whether biometrics is evaluated by policy
        unsigned_applications:
          description: Aggregate-only posture for the unsigned-applications check (BETA). Per-bundle data NEVER leaves the device — only category counts.
          type: object
          properties:
            supported:
              type: boolean
              description: Whether the OS supports the unsigned-applications check (false on Linux/iOS/Android in Phase 2)
            pending:
              type: boolean
              description: Whether the on-device scan is still in progress (true while the first pass runs after install or recheck)
            categories:
              type: object
              additionalProperties:
                type: integer
                minimum: 0
              description: Device-local count per trust-category. Keys are constrained to the documented allowlist.
          required:
            - supported
        unsigned_applications_evaluated_by_policy:
          type: boolean
          description: Whether unsigned applications are evaluated by policy
        install_protection:
          description: Aggregate-only posture for the install-protection check (BETA). macOS Gatekeeper + Windows SmartScreen/Defender PUA.
          type: object
          properties:
            supported:
              type: boolean
              description: Whether the OS supports an install-protection check
            gatekeeper_enabled:
              type: boolean
              description: macOS only — whether Gatekeeper (`spctl --status`) is enabled
            gatekeeper_policy:
              type: string
              description: 'macOS only — Gatekeeper assessment policy (`developer_id`, `app_store`, etc.)'
            smartscreen_explorer:
              type: string
              enum:
                - 'Off'
                - Prompt
                - Block
                - unknown
              description: Windows only — Explorer SmartScreen mode
            defender_pua:
              type: boolean
              description: Windows only — whether Defender PUA protection is enabled
          required:
            - supported
        install_protection_evaluated_by_policy:
          type: boolean
          description: Whether install protection is evaluated by policy
        blocklisted_applications:
          description: Aggregate-only posture for the blocklisted-applications check (BETA). Wire field uses inclusive 'blocklisted' naming even though the desktop module is 'blacklistedapplications'. Per-bundle data NEVER leaves the device — only category counts.
          type: object
          properties:
            supported:
              type: boolean
              description: Whether the OS supports the blocklisted-applications check
            pending:
              type: boolean
              description: Whether the on-device scan is still in progress
            categories:
              type: object
              additionalProperties:
                type: integer
                minimum: 0
              description: Device-local count per blocklist category. Keys are constrained to the documented allowlist.
          required:
            - supported
        blocklisted_applications_evaluated_by_policy:
          type: boolean
          description: Whether blocklisted applications are evaluated by policy
        managed:
          type: boolean
          description: Whether the device is managed
        xfa_version:
          type: string
          description: XFA version
        connect:
          type: boolean
          description: Whether the device is connected
        merged_device_ids:
          type: array
          items:
            type: string
          description: List of merged device IDs
        merged_into_device_id:
          type: string
          description: ID of the device into which this device is merged
        skip:
          type: boolean
          description: Whether the device is skipped
        unsupported:
          type: boolean
          description: Whether the device is unsupported
        discovered:
          type: boolean
          description: Whether the device is discovered
        google_mobile_device_ids:
          type: array
          items:
            type: string
          description: List of Google mobile device IDs
        google_cloud_identity_device_ids:
          type: array
          items:
            type: string
          description: List of Google Cloud Identity device IDs
        microsoft_device_ids:
          type: array
          items:
            type: string
          description: List of Microsoft device IDs
        okta_discovered:
          type: boolean
          description: Whether the device is discovered by Okta
        details_hidden:
          type: boolean
          description: 'Set on a discovered device whose details the organization''s plan does not include (hide_discovered_device_details). The record carries identity only (no check results, decisions or CVEs), plus issues_count and risk. Opening the device returns 403 discovered_device_details_not_in_plan.'
        issues_count:
          type: integer
          description: Number of policy checks failing on the device (warn or block). Only set when details_hidden is true.
        risk:
          type: string
          enum:
            - safe
            - unsafe
            - unknown
            - safe_with_unknowns
          description: Overall risk of the device against the policy. Only set when details_hidden is true.
        has_unknown_checks_required_by_policy:
          type: boolean
          description: Whether the device has unknown checks required by policy
        has_unsafe_checks_evaluated_by_policy:
          type: boolean
          description: Whether the device has unsafe checks evaluated by policy
        has_not_shared_checks_required_by_policy:
          type: boolean
          description: Whether the person does not share a check the policy warns or blocks on (XFA-3686). Such a device is not compliant. Absent when false or not yet evaluated.
        timestamp_last_notified:
          type: string
          format: date-time
          description: Timestamp when the device was last notified
        os_cves:
          type: array
          items:
            $ref: '#/components/schemas/CVE'
          description: List of OS CVEs
        browser_cves:
          type: array
          items:
            $ref: '#/components/schemas/CVE'
          description: List of browser CVEs
        chrome_cves:
          type: array
          items:
            $ref: '#/components/schemas/CVE'
          description: List of Chrome CVEs
        firefox_cves:
          type: array
          items:
            $ref: '#/components/schemas/CVE'
          description: List of Firefox CVEs
        edge_cves:
          type: array
          items:
            $ref: '#/components/schemas/CVE'
          description: List of Edge CVEs
        safari_cves:
          type: array
          items:
            $ref: '#/components/schemas/CVE'
          description: List of Safari CVEs
        opera_cves:
          type: array
          items:
            $ref: '#/components/schemas/CVE'
          description: List of Opera CVEs
        vivaldi_cves:
          type: array
          items:
            $ref: '#/components/schemas/CVE'
          description: List of Vivaldi CVEs
        brave_cves:
          type: array
          items:
            $ref: '#/components/schemas/CVE'
          description: List of Brave CVEs
        arc_cves:
          type: array
          items:
            $ref: '#/components/schemas/CVE'
          description: List of Arc CVEs
      required:
        - device_id
        - timestamp_submitted
        - merged_device_ids
        - google_mobile_device_ids
        - google_cloud_identity_device_ids
        - microsoft_device_ids
        - os_cves
        - browser_cves
        - chrome_cves
        - firefox_cves
        - edge_cves
        - safari_cves
        - opera_cves
        - vivaldi_cves
        - brave_cves
        - arc_cves
    DeviceWithIdentity:
      allOf:
        - $ref: '#/components/schemas/Device'
        - properties:
            email:
              type: string
            note:
              type: string
              description: Note added to the device/shadow
            tags:
              type: array
              items:
                type: string
              description: Tags associated with the device/shadow
            snoozed_until:
              type: integer
              format: int64
              description: Absolute timestamp when the device stops being snoozed
            snoozed_at:
              type: integer
              format: int64
              description: Timestamp when snoozing started
            snoozed_by:
              type: string
              description: Email address of the admin who snoozed the device
            snooze_reason:
              type: string
              description: Optional reason for the snooze
            snooze_mfa:
              type: boolean
              description: Whether MFA prompts are also snoozed
    ErrorResponse:
      type: object
      properties:
        error:
          type: string
          description: Error message
          example: Bad request
        code:
          type: integer
          description: HTTP status code
          example: 400
        details:
          type: object
          description: Additional error details
          additionalProperties: true
      required:
        - error
        - code
    EvaluationSummary:
      type: object
      properties:
        osUpToDate:
          type: integer
          description: Number of devices with OS up to date
        osNotUpToDate:
          type: integer
          description: Number of devices with OS not up to date
        osUnknown:
          type: integer
          description: Number of devices with unknown OS status
        osAutoUpdate:
          type: integer
          description: Number of devices with OS auto update enabled
        osNotAutoUpdate:
          type: integer
          description: Number of devices with OS auto update disabled
        osAutoUpdateUnknown:
          type: integer
          description: Number of devices with unknown OS auto update status
        browserUpToDate:
          type: integer
          description: Number of devices with browser up to date
        browserNotUpToDate:
          type: integer
          description: Number of devices with browser not up to date
        browserUnknown:
          type: integer
          description: Number of devices with unknown browser status
        diskEncryptionActive:
          type: integer
          description: Number of devices with disk encryption active
        diskEncryptionNotActive:
          type: integer
          description: Number of devices with disk encryption not active
        diskEncryptionUnknown:
          type: integer
          description: Number of devices with unknown disk encryption status
        authenticationActive:
          type: integer
          description: Number of devices with authentication active
        authenticationNotActive:
          type: integer
          description: Number of devices with authentication not active
        authenticationUnknown:
          type: integer
          description: Number of devices with unknown authentication status
        antivirusEnabled:
          type: integer
          description: Number of devices with antivirus enabled
        antivirusNotEnabled:
          type: integer
          description: Number of devices with antivirus not enabled
        antivirusUnknown:
          type: integer
          description: Number of devices with unknown antivirus status
        passwordManagerInstalled:
          type: integer
          description: Number of devices with password manager installed
        passwordManagerNotInstalled:
          type: integer
          description: Number of devices with password manager not installed
        passwordManagerUnknown:
          type: integer
          description: Number of devices with unknown password manager status
        biometricsActive:
          type: integer
          description: Number of devices with biometrics active
        biometricsNotActive:
          type: integer
          description: Number of devices with biometrics not active
        biometricsUnknown:
          type: integer
          description: Number of devices with unknown biometrics status
        recentReboot:
          type: integer
          description: Number of devices with recent reboot
        recentRebootNot:
          type: integer
          description: Number of devices without recent reboot
        recentRebootUnknown:
          type: integer
          description: Number of devices with unknown recent reboot status
        windowsRecallAvailable:
          type: integer
          description: Number of devices with Windows Recall available
        windowsRecallNotAvailable:
          type: integer
          description: Number of devices with Windows Recall not available
        windowsRecallUnknown:
          type: integer
          description: Number of devices with unknown Windows Recall status
        firewallEnabled:
          type: integer
          description: Number of devices with firewall enabled
        firewallNotEnabled:
          type: integer
          description: Number of devices with firewall not enabled
        firewallUnknown:
          type: integer
          description: Number of devices with unknown firewall status
        dnsCompliant:
          type: integer
          description: Number of devices with DNS compliant
        dnsNotCompliant:
          type: integer
          description: Number of devices with DNS not compliant
        dnsUnknown:
          type: integer
          description: Number of devices with unknown DNS status
        remoteLoginEnabled:
          type: integer
          description: Number of devices with remote login enabled
        remoteLoginNotEnabled:
          type: integer
          description: Number of devices with remote login not enabled
        remoteLoginUnknown:
          type: integer
          description: Number of devices with unknown remote login status
        remoteManagementEnabled:
          type: integer
          description: Number of devices with remote management enabled
        remoteManagementNotEnabled:
          type: integer
          description: Number of devices with remote management not enabled
        remoteManagementUnknown:
          type: integer
          description: Number of devices with unknown remote management status
        screenSharingEnabled:
          type: integer
          description: Number of devices with screen sharing enabled
        screenSharingNotEnabled:
          type: integer
          description: Number of devices with screen sharing not enabled
        screenSharingUnknown:
          type: integer
          description: Number of devices with unknown screen sharing status
        remoteScriptingEnabled:
          type: integer
          description: Number of devices with remote scripting enabled
        remoteScriptingNotEnabled:
          type: integer
          description: Number of devices with remote scripting not enabled
        remoteScriptingUnknown:
          type: integer
          description: Number of devices with unknown remote scripting status
        safeDevices:
          type: integer
          description: Number of devices that are safe
        unsafeDevices:
          type: integer
          description: Number of devices that are unsafe
        missingRiskInfoDevices:
          type: integer
          description: Number of devices with missing risk information
        unsupportedDevices:
          type: integer
          description: Number of devices that are unsupported
        isJailbroken:
          type: integer
          description: Number of devices that are jailbroken
        isNotJailbroken:
          type: integer
          description: Number of devices that are not jailbroken
        jailbrokenUnknown:
          type: integer
          description: Number of devices with unknown jailbroken status
        isRooted:
          type: integer
          description: Number of devices that are rooted
        isNotRooted:
          type: integer
          description: Number of devices that are not rooted
        rootedUnknown:
          type: integer
          description: Number of devices with unknown rooted status
        DeveloperModeEnabled:
          type: integer
          description: Number of devices with developer mode enabled
        DeveloperModeNotEnabled:
          type: integer
          description: Number of devices with developer mode not enabled
        developerModeUnknown:
          type: integer
          description: Number of devices with unknown developer mode status
        IntegrityProtectionEnabled:
          type: integer
          description: Number of devices with Integrity Protection enabled
        IntegrityProtectionNotEnabled:
          type: integer
          description: Number of devices with Integrity Protection not enabled
        integrityProtectionUnknown:
          type: integer
          description: Number of devices with unknown Integrity Protection status
        SecureBootEnabled:
          type: integer
          description: Number of devices with Secure Boot enabled
        SecureBootNotEnabled:
          type: integer
          description: Number of devices with Secure Boot not enabled
        secureBootUnknown:
          type: integer
          description: Number of devices with unknown Secure Boot status
        FindMyDeviceEnabled:
          type: integer
          description: Number of devices with Find My Device enabled
        FindMyDeviceNotEnabled:
          type: integer
          description: Number of devices with Find My Device not enabled
        findMyDeviceUnknown:
          type: integer
          description: Number of devices with unknown Find My Device status
    GoogleConnection:
      type: object
      properties:
        scopes:
          type: array
          items:
            type: string
        error_mobile_devices_api:
          type: string
          description: Error message for mobile devices API
        email:
          type: string
          description: Email of the Google connection
        error_cloud_identity_api:
          type: string
          description: Error message for Cloud Identity API
        only_unmanaged:
          type: boolean
          description: Only unmanaged devices
        only_groups:
          type: array
          description: only discover devices in these groups (empty means all groups)
          items:
            type: object
            properties:
              name:
                type: string
              id:
                type: string
        exclude_desktop:
          type: boolean
          description: Exclude desktop devices
        exclude_mobile:
          type: boolean
          description: Exclude mobile devices
        last_error:
          type: string
          description: Last error message
        first_full_read_done:
          type: boolean
          readOnly: true
          description: Whether the first full discovery read completed successfully
      required:
        - scopes
        - only_groups
    GroupedDevice:
      type: object
      properties:
        shadows:
          type: object
          additionalProperties:
            type: array
            items:
              $ref: '#/components/schemas/DeviceWithIdentity'
        last_evaluated_key:
          type: string
      required:
        - shadows
        - last_evaluated_key
    InvitationRequest:
      type: object
      properties:
        organization_id:
          type: string
          description: ID of the organization
        email:
          type: string
          description: Email of the user
        send_email:
          type: boolean
          description: Whether to send an email invitation. Defaults to true.
        send_slack_message:
          type: boolean
          description: Whether to send a Slack invitation message. Defaults to false.
        send_teams_message:
          type: boolean
          description: Whether to send a Microsoft Teams invitation message. Defaults to false.
      required:
        - organization_id
        - email
    Invoice:
      type: object
      properties:
        number:
          type: string
          description: Invoice number
        date:
          type: string
          format: date
          description: Invoice date
        amount:
          type: number
          format: float
          description: Invoice amount
    InvitationResponse:
      type: object
      properties:
        invitation_token:
          type: string
          description: Invitation token
        invitation_url:
          type: string
          description: url to invitation
        quota:
          $ref: '#/components/schemas/ManualAwarenessQuota'
        invited_by:
          type: string
          description: Authenticated inviter email or stable automated origin identifier
      required:
        - invitation_token
        - invitation_url
    InvitationTokenResponse:
      type: object
      properties:
        invitation_token:
          type: string
          description: Organization invitation token used for managed deployment
      required:
        - invitation_token
    InvitationInformationResponse:
      type: object
      properties:
        organization_id:
          type: string
          description: ID of the organization
        organization_name:
          type: string
          description: Name of the organization
        email:
          type: string
          description: Email of the user
        timestamp:
          type: string
          format: date-time
          description: Timestamp of the invitation
        invitation_token:
          type: string
          description: Invitation token
        logo_url:
          type: string
          description: 'Logo of the inviting organization, as a base64 data URL (`data:image/...;base64,...`). Every logo uploaded through this API is stored in that form. Absent when the organization has no logo, when its logo is a legacy http(s) URL, or when the logo could not be read quickly enough; the invitation is returned either way.'
    InvitationInformationWithoutTokenResponse:
      type: object
      properties:
        organization_id:
          type: string
          description: ID of the organization
        organization_name:
          type: string
          description: Name of the organization
        email:
          type: string
          description: Email of the user
        timestamp:
          type: string
          format: date-time
          description: Timestamp of the invitation
        invited_by:
          type: string
          description: Authenticated inviter email or stable automated origin identifier
    InvitationResendRequest:
      type: object
      properties:
        reminder_sent_timestamp:
          type: string
          format: date-time
          description: Timestamp of the reminder sent
    InvitationUpdateRequest:
      type: object
      properties:
        language:
          type: string
          description: Language of the invitation
      required:
        - language
    ListAffiliation:
      type: object
      properties:
        affiliations:
          type: array
          items:
            $ref: '#/components/schemas/Affiliation'
    ListTransactions:
      type: object
      properties:
        devices:
          type: array
          items:
            $ref: '#/components/schemas/Transactions'
    ListDevicesWithIdentityResponse:
      type: object
      properties:
        devices:
          type: array
          items:
            $ref: '#/components/schemas/DeviceWithIdentity'
    ManualAwarenessQuota:
      type: object
      description: Manual-awareness message counter reported after a send. A limit of 0 means unlimited.
      properties:
        used:
          type: integer
          description: Number of manual-awareness messages used in the current period
        limit:
          type: integer
          description: Manual-awareness message limit for the current period. 0 means unlimited.
        remaining:
          type: integer
          description: Number of manual-awareness messages remaining in the current period
        period:
          type: string
          enum:
            - trial
            - month
          description: Period the quota applies to
      required:
        - used
        - limit
        - remaining
        - period
    ManualAwarenessSendResponse:
      type: object
      description: Response body for send endpoints that count against the manual-awareness quota.
      properties:
        quota:
          $ref: '#/components/schemas/ManualAwarenessQuota'
    MicrosoftConnection:
      type: object
      properties:
        scopes:
          type: array
          items:
            type: string
          description: List of scopes for the Microsoft connection
        last_error:
          type: string
          description: Last error message
        only_unmanaged:
          type: boolean
          description: Only discover unmanaged devices
        only_groups:
          type: array
          description: Only discover devices from users in these groups (no groups means all groups)
          items:
            type: object
            properties:
              name:
                type: string
                description: Name of the group
              id:
                type: string
                description: ID of the group
        exclude_desktop:
          type: boolean
          description: Exclude desktop devices
        exclude_mobile:
          type: boolean
          description: Exclude mobile devices
        last_sync:
          type: integer
          description: Last time the devices were discovered
        discovered_until:
          type: integer
          description: Unix time up until which devices have been discovered (for pagination)
        first_full_read_done:
          type: boolean
          readOnly: true
          description: Whether the first full discovery read completed successfully
      required:
        - scopes
        - only_groups
    TeamsDisconnectTeardownCallbackRequest:
      type: object
      properties:
        organization_id:
          type: string
          description: The ID of the organization completing Teams disconnect teardown
        state:
          type: string
          description: The admin-consent state returned by Microsoft
        code:
          type: string
          description: The delegated authorization code returned by Microsoft
      required:
        - organization_id
        - state
        - code
    TeamsDisconnectTeardownCallbackResponse:
      type: object
      properties:
        catalog:
          type: string
          enum:
            - deleted
            - skipped_shared_tenant
            - skipped_missing_catalog
            - error
          description: Catalog app teardown status
        tenant_shared:
          type: boolean
          description: Whether another active Teams connection shares the Microsoft tenant
        entra:
          type: object
          properties:
            show:
              type: boolean
            app_id:
              type: string
            app_name:
              type: string
            deep_link:
              type: string
          required:
            - show
            - app_id
            - app_name
            - deep_link
        uninstall:
          type: string
          enum:
            - queued
            - skipped
          description: User-installation teardown status
      required:
        - catalog
        - tenant_shared
        - entra
        - uninstall
    TeamsDisconnectTeardownConsentURLRequest:
      type: object
      properties:
        organization_id:
          type: string
          description: The ID of the organization that owns the Teams connection
        connection_id:
          type: string
          description: The Teams messaging connection ID to tear down
        redirect_uri:
          type: string
          description: The dashboard URI where Microsoft redirects after teardown admin consent
      required:
        - organization_id
        - connection_id
        - redirect_uri
    TeamsDisconnectTeardownConsentURLResponse:
      type: object
      properties:
        state:
          type: string
        consent_url:
          type: string
      required:
        - state
        - consent_url
    OAuthConfiguration:
      type: object
      properties:
        enabled:
          type: boolean
          description: Indicates if OAuth is enabled
        redirect_url_to_client:
          type: string
          description: URL to redirect to the client
        token_endpoint_of_provider:
          type: string
          description: Token endpoint of the provider
        authorize_endpoint_of_provider:
          type: string
          description: 'The provider''s OAuth2 authorization endpoint. When set, XFA performs the device check before redirecting the user to the provider''s authorize endpoint, so the provider''s authorization code is minted after the device check rather than before it (which prevents the code expiring during the check). When omitted, the existing flow is used unchanged.'
      required:
        - enabled
    OktaConnection:
      type: object
      properties:
        okta_domain:
          type: string
          description: Domain of the Okta connection
        client_id:
          type: string
          description: Client ID for the Okta connection
        client_secret:
          type: string
          description: Client secret for the Okta connection
        last_error:
          type: string
          description: Last error message
        last_sync:
          type: integer
          description: Last time the devices were discovered
        discovered_until:
          type: integer
          description: Unix time up until which devices have been discovered (for pagination)
        first_full_read_done:
          type: boolean
          readOnly: true
          description: Whether the first full discovery read completed successfully
      required:
        - okta_domain
        - client_id
        - client_secret
    Organization:
      type: object
      properties:
        organization_id:
          type: string
          description: ID of Organization
        name:
          type: string
          description: Name of Organization
        address:
          type: string
          description: Address of Organization
        zip_code:
          type: string
          description: Zip Code of Organization
        city:
          type: string
          description: City of Organization
        country:
          type: string
          description: Country of Organization
        vat:
          type: string
          description: VAT of Organization
        tax_number:
          type: string
          description: Tax Number of Organization
        phone_number:
          type: string
          description: Phone Number of Organization
        billing_email:
          type: string
          description: Billing Email of Organization
        alpha_features:
          type: boolean
          description: Alpha features enabled
        beta_features:
          type: boolean
          description: Beta features enabled
        feature_flags:
          type: array
          description: Feature flags enabled for this organization
          items:
            $ref: '#/components/schemas/FeatureFlag'
        default_policy_id:
          type: string
          description: Default Policy ID of Organization
      required:
        - organization_id
        - name
        - address
        - zip_code
        - city
        - country
        - vat
        - tax_number
        - phone_number
        - billing_email
    FeatureFlag:
      type: string
      description: 'An organization feature flag. Values are validated by xfa-organizations-service (`FeatureFlag.IsValid()`), which is the single source of truth; this contract is intentionally left open so that adding a new flag does not require an xfa-api change. Currently known values: phishing_lab, runaway_ai, edr-detection, safe_browsing, slack, teams, self_invite, mem_export, unattended_remote_access, aikido_enabled, application_checks_enabled, idp, play_protect, mdm_enrollment, passkeys, admin_mfa_approval.'
      example: play_protect
    Language:
      type: string
      description: 'Language for end-user emails when the recipient has not picked one; a user''s own choice always wins. The set mirrors the email templates shipped by xfa-notification-service. An empty string is the canonical way to clear the organization default, on both PUT and PATCH, so the whole organization can be saved in one request; xfa-organizations-service stores it as an absent attribute.'
      enum:
        - ''
        - en
        - nl
        - fr
        - de
        - es
    OrganizationsListResponse:
      type: object
      properties:
        total:
          type: integer
          description: The total number of organizations
        start:
          type: integer
          description: The index of the first organization returned
        limit:
          type: integer
          description: The maximum number of organizations returned
        items:
          type: array
          items:
            $ref: '#/components/schemas/OrganizationResponse'
    OrganizationCounters:
      type: object
      properties:
        organization_id:
          type: string
          description: ID of Organization
        date:
          type: string
          description: Date of the counter
        type:
          type: string
          description: Type of the counter
        warned:
          type: integer
          description: Number of warned devices
        blocked:
          type: integer
          description: Number of blocked devices
        secure_sign_ins:
          type: integer
          description: Number of sign-ins with no warning or block
        skipped:
          type: integer
          description: Number of successful full transaction skips with skip_limits active and a verified user
        snoozed:
          type: integer
          description: Number of sign-ins where the user snoozed a warning
        granted:
          type: integer
          description: Number of sign-ins an administrator granted access to; not part of the verification total
        verification_email:
          type: integer
          description: Number of verification emails
        risk_email:
          type: integer
          description: Number of risk emails
      required:
        - organization_id
        - date
        - type
        - warned
        - blocked
        - secure_sign_ins
        - skipped
        - snoozed
        - granted
        - verification_email
        - risk_email
    OrganizationsCreateResponse:
      type: object
      properties:
        organization_id:
          type: string
          description: ID of Organization
    OrganizationsCreateRequestBody:
      type: object
      properties:
        name:
          type: string
          description: Name of Organization
        referral_code:
          type: string
          description: 'Referral code this signup came through, resolved to the referrer''s email'
      required:
        - name
    AwarenessSchedule:
      type: object
      readOnly: true
      description: 'Next nominal hourly Awareness evaluation in production (minute 30, UTC), not a guaranteed delivery time. Recipient cooldowns, scope, billing and channel availability are checked at execution. Absent outside production or when all automations are disabled. Reload to refresh expired times. Risk alerts currently require notify_unsafe_devices, including Slack/Teams.'
      properties:
        auto_invite:
          $ref: '#/components/schemas/AwarenessAutomationSchedule'
        setup_reminder:
          $ref: '#/components/schemas/AwarenessAutomationSchedule'
        risk_alert:
          $ref: '#/components/schemas/AwarenessAutomationSchedule'
    AwarenessAutomationSchedule:
      type: object
      required:
        - next_run_at
      properties:
        next_run_at:
          type: string
          format: date-time
          description: 'Next scheduled Awareness evaluation, in UTC; actual delivery is conditional.'
    OrganizationFull:
      type: object
      properties:
        awareness_schedule:
          $ref: '#/components/schemas/AwarenessSchedule'
        organization_id:
          type: string
          description: ID of Organization
        name:
          type: string
          description: Name of Organization
        address:
          type: string
          description: Address of Organization
        zip_code:
          type: string
          description: Zip Code of Organization
        city:
          type: string
          description: City of Organization
        country:
          type: string
          description: Country of Organization
        vat:
          type: string
          description: VAT of Organization
        tax_number:
          type: string
          description: Tax Number of Organization
        phone_number:
          type: string
          description: Phone Number of Organization
        billing_email:
          type: string
          description: Billing Email of Organization
        billing_name:
          type: string
          description: Billing Name of Organization
        billing_first_name:
          type: string
          description: Billing First Name of Organization
        billing_last_name:
          type: string
          description: Billing Last Name of Organization
        deleted:
          type: boolean
          description: Whether the organization is deleted
        logo_url:
          type: string
          description: URL of the logo
        notify_no_managed_devices:
          type: boolean
          description: Notify no managed devices
        notify_no_desktop_devices:
          type: boolean
          description: Notify no desktop devices
        notify_no_mobile_devices:
          type: boolean
          description: Notify no mobile devices
        notify_discovered_devices:
          type: boolean
          description: Notify discovered devices
        notify_discovered_devices_frequency_in_days:
          type: integer
          description: Frequency of notification for discovered devices
        invite_discovered_devices:
          type: boolean
          description: Invite discovered devices
        default_language:
          $ref: '#/components/schemas/Language'
        self_invite_enabled:
          type: boolean
          description: Allow verified native app users to request self-invite when eligible
        exclude_from_customer_metrics:
          type: boolean
          description: Keeps this organization out of company-wide customer metrics. Set on XFA's own organizations. Only system administrators may change it; an org admin sending the stored value back is accepted.
        notify_unsafe_devices:
          type: boolean
          description: Notify unsafe devices
        notify_unsafe_devices_frequency_in_days:
          type: integer
          description: Frequency of notification for unsafe devices
        slack_enabled:
          type: boolean
          description: Enable Slack DMs for device risk notifications
        slack_notify_unsafe_devices:
          type: boolean
          description: Send Slack DMs to users about unsafe devices
        slack_notify_discovered_devices:
          type: boolean
          description: Send Slack DMs to users about discovered devices
        slack_invite_discovered_devices:
          type: boolean
          description: Send invitation Slack DMs to users with discovered devices
        manual_invite_send_slack:
          type: boolean
          description: Last-used Slack toggle state in the manual Invite users popup.
        teams_notify_unsafe_devices:
          type: boolean
          description: Send Teams DMs to users about unsafe devices
        teams_notify_discovered_devices:
          type: boolean
          description: Send Teams DMs to users about discovered devices
        teams_invite_discovered_devices:
          type: boolean
          description: Send invitation Teams DMs to users with discovered devices
        manual_invite_send_teams:
          type: boolean
          description: Last-used Microsoft Teams toggle state in the manual Invite users popup.
        notify_only_groups:
          type: array
          items:
            type: object
            properties:
              name:
                type: string
              id:
                type: string
        default_policy_id:
          type: string
          description: Default Policy ID of Organization
        feature_flags:
          type: array
          description: Feature flags enabled for this organization
          items:
            $ref: '#/components/schemas/FeatureFlag'
        getting_started_state:
          type: string
          description: JSON blob owned by the dashboard's Getting Started journey; opaque to the backend.
        referred_by:
          type: string
          description: 'Email of the dashboard user whose referral code this organization signed up with, if any.'
        timestamp:
          type: string
          format: date-time
          description: Created timestamp of the organization
      required:
        - organization_id
        - name
        - address
        - zip_code
        - city
        - country
        - vat
        - tax_number
        - phone_number
        - billing_email
        - timestamp
    OrganizationResponse:
      type: object
      properties:
        awareness_schedule:
          $ref: '#/components/schemas/AwarenessSchedule'
        organization_id:
          type: string
          description: ID of Organization
        name:
          type: string
          description: Name of Organization
        address:
          type: string
          description: Address of Organization
        zip_code:
          type: string
          description: Zip Code of Organization
        city:
          type: string
          description: City of Organization
        country:
          type: string
          description: Country of Organization
        vat:
          type: string
          description: VAT of Organization
        tax_number:
          type: string
          description: Tax Number of Organization
        phone_number:
          type: string
          description: Phone Number of Organization
        billing_email:
          type: string
          description: Billing Email of Organization
        billing_name:
          type: string
          description: Billing Name of Organization
        billing_first_name:
          type: string
          description: Billing First Name of Organization
        billing_last_name:
          type: string
          description: Billing Last Name of Organization
        deleted:
          type: boolean
          description: Whether the organization is deleted
        logo_url:
          type: string
          description: URL of the logo
        notify_no_managed_devices:
          type: boolean
          description: Notify no managed devices
        notify_no_desktop_devices:
          type: boolean
          description: Notify no desktop devices
        notify_no_mobile_devices:
          type: boolean
          description: Notify no mobile devices
        notify_discovered_devices:
          type: boolean
          description: Notify discovered devices
        notify_discovered_devices_frequency_in_days:
          type: integer
          description: Frequency of notification for discovered devices
        invite_discovered_devices:
          type: boolean
          description: Invite discovered devices
        default_language:
          $ref: '#/components/schemas/Language'
        self_invite_enabled:
          type: boolean
          description: Allow verified native app users to request self-invite when eligible
        exclude_from_customer_metrics:
          type: boolean
          description: Keeps this organization out of company-wide customer metrics. Set on XFA's own organizations. Only system administrators may change it; an org admin sending the stored value back is accepted.
        notify_unsafe_devices:
          type: boolean
          description: Notify unsafe devices
        notify_unsafe_devices_frequency_in_days:
          type: integer
          description: Frequency of notification for unsafe devices
        slack_enabled:
          type: boolean
          description: Enable Slack DMs for device risk notifications
        slack_notify_unsafe_devices:
          type: boolean
          description: Send Slack DMs to users about unsafe devices
        slack_notify_discovered_devices:
          type: boolean
          description: Send Slack DMs to users about discovered devices
        slack_invite_discovered_devices:
          type: boolean
          description: Send invitation Slack DMs to users with discovered devices
        manual_invite_send_slack:
          type: boolean
          description: Last-used Slack toggle state in the manual Invite users popup.
        teams_notify_unsafe_devices:
          type: boolean
          description: Send Teams DMs to users about unsafe devices
        teams_notify_discovered_devices:
          type: boolean
          description: Send Teams DMs to users about discovered devices
        teams_invite_discovered_devices:
          type: boolean
          description: Send invitation Teams DMs to users with discovered devices
        manual_invite_send_teams:
          type: boolean
          description: Last-used Microsoft Teams toggle state in the manual Invite users popup.
        notify_only_groups:
          type: array
          items:
            type: object
            properties:
              name:
                type: string
              id:
                type: string
        default_policy_id:
          type: string
          description: Default Policy ID of Organization
        use_user_agent_and_client_hints:
          type: boolean
          description: Use user-agent and client hints from browser to complete checks
        use_discovery_data:
          type: boolean
          description: Use Discovery data to complete checks
        google_chrome_device_trust:
          type: boolean
          description: Google Chrome device trust
        microsoft_edge_device_trust:
          type: object
          properties:
            tenant_id:
              type: string
              description: Tenant ID for device trust
            client_id:
              type: string
              description: Client ID for device trust
        feature_flags:
          type: array
          description: Feature flags enabled for this organization
          items:
            $ref: '#/components/schemas/FeatureFlag'
        getting_started_state:
          type: string
          description: JSON blob owned by the dashboard's Getting Started journey; opaque to the backend.
        referred_by:
          type: string
          description: 'Email of the dashboard user whose referral code this organization signed up with, if any.'
        timestamp:
          type: string
          format: date-time
          description: Created timestamp of the organization
        active_users:
          $ref: '#/components/schemas/ActiveUsers'
        invoice:
          $ref: '#/components/schemas/Invoice'
        settings:
          $ref: '#/components/schemas/Settings'
      required:
        - organization_id
        - name
        - address
        - zip_code
        - city
        - country
        - vat
        - tax_number
        - phone_number
        - billing_email
        - timestamp
    OrganizationsUpdateRequestBody:
      type: object
      properties:
        name:
          type: string
          description: Name of Organization
        notify_discovered_devices:
          type: boolean
          description: Notify discovered devices
        invite_discovered_devices:
          type: boolean
          description: Invite discovered devices
        default_language:
          $ref: '#/components/schemas/Language'
        self_invite_enabled:
          type: boolean
          description: Allow verified native app users to request self-invite when eligible
        exclude_from_customer_metrics:
          type: boolean
          description: Keeps this organization out of company-wide customer metrics. Set on XFA's own organizations. Only system administrators may change it; an org admin sending the stored value back is accepted.
        notify_unsafe_devices:
          type: boolean
          description: Notify unsafe devices
        slack_enabled:
          type: boolean
          description: Enable Slack DMs for device risk notifications
        slack_notify_unsafe_devices:
          type: boolean
          description: Send Slack DMs to users about unsafe devices
        slack_notify_discovered_devices:
          type: boolean
          description: Send Slack DMs to users about discovered devices
        slack_invite_discovered_devices:
          type: boolean
          description: Send invitation Slack DMs to users with discovered devices
        manual_invite_send_slack:
          type: boolean
          description: Last-used Slack toggle state in the manual Invite users popup.
        teams_notify_unsafe_devices:
          type: boolean
          description: Send Teams DMs to users about unsafe devices
        teams_notify_discovered_devices:
          type: boolean
          description: Send Teams DMs to users about discovered devices
        teams_invite_discovered_devices:
          type: boolean
          description: Send invitation Teams DMs to users with discovered devices
        manual_invite_send_teams:
          type: boolean
          description: Last-used Microsoft Teams toggle state in the manual Invite users popup.
        use_user_agent_and_client_hints:
          type: boolean
          description: Use user-agent and client hints from browser to complete checks
        use_discovery_data:
          type: boolean
          description: Use Discovery data to complete checks
        google_chrome_device_trust:
          type: boolean
          description: Google Chrome device trust
        microsoft_edge_device_trust:
          type: object
          properties:
            tenant_id:
              type: string
              description: Tenant ID for device trust
            client_id:
              type: string
              description: Client ID for device trust
            client_secret:
              type: string
              description: Client Secret for device trust
        feature_flags:
          type: array
          description: Feature flags enabled for this organization
          items:
            $ref: '#/components/schemas/FeatureFlag'
        tax_number:
          type: string
          description: Tax Number of Organization
        phone_number:
          type: string
          description: Phone Number of Organization
        getting_started_state:
          type: string
          description: JSON blob owned by the dashboard's Getting Started journey; opaque to the backend.
      required:
        - name
    PasswordManager:
      type: object
      properties:
        onepassword:
          type: boolean
          description: Whether 1Password is used
        lastpass:
          type: boolean
          description: Whether LastPass is used
        dashlane:
          type: boolean
          description: Whether Dashlane is used
        bitwarden:
          type: boolean
          description: Whether Bitwarden is used
        keepass:
          type: boolean
          description: Whether KeePass is used
        nordpass:
          type: boolean
          description: Whether NordPass is used
        protonpass:
          type: boolean
          description: Whether ProtonPass is used
        icloud_passwords:
          type: boolean
          description: Whether iCloud Passwords is used
        dropbox_passwords:
          type: boolean
          description: Whether Dropbox Passwords is used
        passbolt:
          type: boolean
          description: Whether Passbolt is used
        enpass:
          type: boolean
          description: Whether Enpass is used
        avast_passwords:
          type: boolean
          description: Whether Avast Passwords is used
        avira_passwords:
          type: boolean
          description: Whether Avira Passwords is used
    Policies:
      description: |
        Shared policy representation. On PUT, each OS-specific override
        (`windows_os`, `macos_os`, `linux_os`, `android_os`, `ios_os`, and
        `ipados_os`) uses
        presence-aware update semantics: an omitted key preserves the stored
        override, `null` removes it and resumes inheritance from `os`, `{}` stores
        an explicitly disabled override without falling back, and a non-empty
        object replaces it with a custom version policy.

        These rules apply both to the policy PUT request body and to the same
        policy object when it is nested under `Application.Policies` in an
        application PUT request. For example, use
        `{"Policies":{"windows_os":null}}` to clear an inline Windows override.
      example:
        os_autoupdate:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        no_tampered_apps:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        firefox_enhanced_tracking_protection:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        antivirus:
          warn: true
          requirements:
            linux:
              allowed_products: []
            windows:
              allowed_products: []
            macos:
              allowed_products: []
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        install_protection:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        unsafe_ai_mode:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        no_cryptominers:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        created_at_epoch_seconds: 0
        screen_sharing:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        remote_management:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        skip_desktop: true
        developer_mode:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        unattended_remote_access:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        skip_limit: ''
        aikido_endpoint:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
          endpoint_token: endpoint_token
        secrets_in_environment:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        updated_by_email: updated_by_email
        disk_encryption:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        ipados_os:
          WarnTime: 9
          BlockTimeOption: direct
          GoalTime: 6
          older_supported_major_versions:
            dont_warn: true
            dont_block: true
          BlockTime: 9
          WarnTimeOption: direct
          beta_versions:
            dont_warn: true
            dont_block: true
        android_os:
          WarnTime: 1
          BlockTimeOption: direct
          GoalTime: 7
          older_supported_major_versions:
            dont_warn: true
            dont_block: true
          BlockTime: 6
          WarnTimeOption: direct
          beta_versions:
            dont_warn: true
            dont_block: true
        no_unsigned_apps:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        xfa_version:
          GoalTimeInDays: 6
          BlockTimeOption: direct
          older_supported_major_versions:
            dont_warn: true
            dont_block: true
          WarnTimeInDays: 1
          BlockTimeInDays: 2
          WarnTimeOption: direct
          beta_versions:
            dont_warn: true
            dont_block: true
        no_revoked_signature_apps:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        ios_os:
          WarnTime: 1
          BlockTimeOption: direct
          GoalTime: 5
          older_supported_major_versions:
            dont_warn: true
            dont_block: true
          BlockTime: 4
          WarnTimeOption: direct
          beta_versions:
            dont_warn: true
            dont_block: true
        dns:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          validation_mode: exact_match
          block: true
          dns_servers:
            - dns_servers
            - dns_servers
        chrome_do_not_track:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        no_third_party_ai_coding:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        updated_at_epoch_seconds: 6
        no_virtualization:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        windows_os:
          WarnTime: 2
          BlockTimeOption: direct
          GoalTime: 9
          older_supported_major_versions:
            dont_warn: true
            dont_block: true
          BlockTime: 7
          WarnTimeOption: direct
          beta_versions:
            dont_warn: true
            dont_block: true
        chrome_safebrowsing_enabled:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        organization_id: organization_id
        find_my_device:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        name: name
        no_unnotarized_apps:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        pdf_readers:
          WarnTime: 1
          BlockTimeOption: direct
          GoalTime: 5
          older_supported_major_versions:
            dont_warn: true
            dont_block: true
          BlockTime: 5
          WarnTimeOption: direct
          beta_versions:
            dont_warn: true
            dont_block: true
        installed: true
        autonomous_agents_present:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        chrome_dns_over_https:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        chrome_safebrowsing_enhanced:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        policy_id: policy_id
        linux_os:
          WarnTime: 7
          BlockTimeOption: direct
          GoalTime: 1
          older_supported_major_versions:
            dont_warn: true
            dont_block: true
          BlockTime: 1
          WarnTimeOption: direct
          beta_versions:
            dont_warn: true
            dont_block: true
        no_games:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        skip: true
        windows_recall:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        firefox_https_only:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        no_permission_hungry:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        integrity_protection:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        unsupported: true
        no_hacking_pentest:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        aikido_safe_chain:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        browser:
          WarnTime: 1
          BlockTimeOption: direct
          GoalTime: 5
          older_supported_major_versions:
            dont_warn: true
            dont_block: true
          BlockTime: 5
          WarnTimeOption: direct
          beta_versions:
            dont_warn: true
            dont_block: true
        remote_login:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        rooted:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        remote_scripting:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        skip_mobile: true
        created_by_email: created_by_email
        no_jailbreak_rooting:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        reboot:
          GoalTimeInDays: 6
          BlockTimeOption: direct
          WarnTimeInDays: 6
          BlockTimeInDays: 3
          WarnTimeOption: direct
        no_adhoc_signed_apps:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        os:
          WarnTime: 1
          BlockTimeOption: direct
          GoalTime: 5
          older_supported_major_versions:
            dont_warn: true
            dont_block: true
          BlockTime: 5
          WarnTimeOption: direct
          beta_versions:
            dont_warn: true
            dont_block: true
        secure_boot:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        firefox_enhanced_tracking_protection_strict:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        no_piracy_p2p:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        jailbroken:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        agentless_allowed: true
        no_vpn_clients:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        intune:
          warn: true
          goal: true
          external_enrollment_allowed: true
          escalation:
            mode: grace_days
            block_after_days: 1
          tenant_ids:
            - tenant_ids
            - tenant_ids
          block: true
        macos_os:
          WarnTime: 3
          BlockTimeOption: direct
          GoalTime: 4
          older_supported_major_versions:
            dont_warn: true
            dont_block: true
          BlockTime: 2
          WarnTimeOption: direct
          beta_versions:
            dont_warn: true
            dont_block: true
        no_untrusted_signer_apps:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        biometrics:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        screen_lock:
          max_timeout: 9
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        firewall:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        firefox_dns_over_https:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        unguarded_elevation:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        vanta:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        password_manager:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
        no_experimental_browsers:
          warn: true
          goal: true
          escalation:
            mode: grace_days
            block_after_days: 1
          block: true
      properties:
        policy_id:
          description: Unique identifier for the policy
          type: string
        organization_id:
          description: Organization identifier
          type: string
        created_by_email:
          description: Email of the user who created the policy
          type: string
        created_at_epoch_seconds:
          description: Unix epoch seconds when the policy was created
          format: int64
          type: integer
        updated_by_email:
          description: Email of the user who last updated the policy
          type: string
        updated_at_epoch_seconds:
          description: Unix epoch seconds when the policy was last updated
          format: int64
          type: integer
        name:
          description: Policy name
          type: string
        installed:
          description: Require the native application to be installed
          type: boolean
        unsupported:
          description: Skip unsupported devices automatically
          type: boolean
        skip:
          description: Allow users to skip the token flow
          type: boolean
        skip_limit:
          allOf:
            - $ref: '#/components/schemas/SkipLimit'
          nullable: true
        skip_mobile:
          description: Allow users to skip the token flow on mobile
          type: boolean
        skip_desktop:
          description: Allow users to skip the token flow on desktop
          type: boolean
        agentless_allowed:
          description: Allow agentless providing of posture
          type: boolean
        os:
          $ref: '#/components/schemas/VersionPolicy'
        windows_os:
          allOf:
            - $ref: '#/components/schemas/VersionPolicy'
          description: 'Optional Windows-specific OS version override. Omit to preserve or inherit the generic OS policy, send null on PUT to clear the override, or send an empty object to explicitly disable the Windows version check.'
          example:
            WarnTime: 2
            BlockTimeOption: direct
            GoalTime: 9
            older_supported_major_versions:
              dont_warn: true
              dont_block: true
            BlockTime: 7
            WarnTimeOption: direct
            beta_versions:
              dont_warn: true
              dont_block: true
          nullable: true
        macos_os:
          allOf:
            - $ref: '#/components/schemas/VersionPolicy'
          description: 'Optional macOS-specific OS version override. Omit to preserve or inherit the generic OS policy, send null on PUT to clear the override, or send an empty object to explicitly disable the macOS version check.'
          example:
            WarnTime: 3
            BlockTimeOption: direct
            GoalTime: 4
            older_supported_major_versions:
              dont_warn: true
              dont_block: true
            BlockTime: 2
            WarnTimeOption: direct
            beta_versions:
              dont_warn: true
              dont_block: true
          nullable: true
        linux_os:
          allOf:
            - $ref: '#/components/schemas/VersionPolicy'
          description: 'Optional Linux and UNIX-specific OS version override. Omit to preserve or inherit the generic OS policy, send null on PUT to clear the override, or send an empty object to explicitly disable the Linux version check.'
          example:
            WarnTime: 7
            BlockTimeOption: direct
            GoalTime: 1
            older_supported_major_versions:
              dont_warn: true
              dont_block: true
            BlockTime: 1
            WarnTimeOption: direct
            beta_versions:
              dont_warn: true
              dont_block: true
          nullable: true
        android_os:
          allOf:
            - $ref: '#/components/schemas/VersionPolicy'
          description: 'Optional Android-specific OS version override. Omit to preserve or inherit the generic OS policy, send null on PUT to clear the override, or send an empty object to explicitly disable the Android version check.'
          example:
            WarnTime: 1
            BlockTimeOption: direct
            GoalTime: 7
            older_supported_major_versions:
              dont_warn: true
              dont_block: true
            BlockTime: 6
            WarnTimeOption: direct
            beta_versions:
              dont_warn: true
              dont_block: true
          nullable: true
        ios_os:
          allOf:
            - $ref: '#/components/schemas/VersionPolicy'
          description: 'Optional iOS-specific OS version override. Omit to preserve or inherit the generic OS policy, send null on PUT to clear the override, or send an empty object to explicitly disable the iOS version check.'
          example:
            WarnTime: 1
            BlockTimeOption: direct
            GoalTime: 5
            older_supported_major_versions:
              dont_warn: true
              dont_block: true
            BlockTime: 4
            WarnTimeOption: direct
            beta_versions:
              dont_warn: true
              dont_block: true
          nullable: true
        ipados_os:
          allOf:
            - $ref: '#/components/schemas/VersionPolicy'
          description: 'Optional iPadOS-specific OS version override. Omit to preserve or inherit the generic OS policy, send null on PUT to clear the override, or send an empty object to explicitly disable the iPadOS version check.'
          example:
            WarnTime: 9
            BlockTimeOption: direct
            GoalTime: 6
            older_supported_major_versions:
              dont_warn: true
              dont_block: true
            BlockTime: 9
            WarnTimeOption: direct
            beta_versions:
              dont_warn: true
              dont_block: true
          nullable: true
        os_autoupdate:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if OS auto-update is not enabled
              type: boolean
            block:
              description: Block users if OS auto-update is not enabled
              type: boolean
            goal:
              description: Goal - whether OS auto-update should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        browser:
          $ref: '#/components/schemas/VersionPolicy'
        pdf_readers:
          $ref: '#/components/schemas/VersionPolicy'
        disk_encryption:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if disk is not encrypted
              type: boolean
            block:
              description: Block users if disk is not encrypted
              type: boolean
            goal:
              description: Goal - whether disk encryption should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        screen_lock:
          example:
            max_timeout: 9
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if screen lock is not enabled or timeout exceeds max_timeout
              type: boolean
            block:
              description: Block users if screen lock is not enabled or timeout exceeds max_timeout
              type: boolean
            goal:
              description: Goal - whether screen lock should be enabled
              type: boolean
            max_timeout:
              description: Maximum allowed screen lock timeout in seconds
              type: integer
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        antivirus:
          $ref: '#/components/schemas/AntivirusPolicy'
        password_manager:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if password manager is not enabled
              type: boolean
            block:
              description: Block users if password manager is not enabled
              type: boolean
            goal:
              description: Goal - whether password manager should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        biometrics:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if biometric is not enabled
              type: boolean
            block:
              description: Block users if biometric is not enabled
              type: boolean
            goal:
              description: Goal - whether biometric should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        reboot:
          example:
            GoalTimeInDays: 6
            BlockTimeOption: direct
            WarnTimeInDays: 6
            BlockTimeInDays: 3
            WarnTimeOption: direct
          properties:
            WarnTimeInDays:
              description: Warn users if they have not reboot their device more than this many days
              type: integer
            WarnTimeOption:
              $ref: '#/components/schemas/PolicyThresholdTimeOption'
            BlockTimeInDays:
              description: Block users if they have not reboot their device more than this many days
              type: integer
            BlockTimeOption:
              $ref: '#/components/schemas/PolicyThresholdTimeOption'
            GoalTimeInDays:
              description: Goal - days that devices are allowed to be without rebooting
              type: integer
          type: object
        windows_recall:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if they have not disabled windows recall
              type: boolean
            block:
              description: Block users if they have not disabled windows recall
              type: boolean
            goal:
              description: Goal - whether windows recall should be disabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        xfa_version:
          $ref: '#/components/schemas/VersionPolicyInDays'
        firewall:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if firewall is not enabled
              type: boolean
            block:
              description: Block users if firewall is not enabled
              type: boolean
            goal:
              description: Goal - whether firewall should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        dns:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            validation_mode: exact_match
            block: true
            dns_servers:
              - dns_servers
              - dns_servers
          properties:
            dns_servers:
              description: List of required DNS servers
              items:
                type: string
              type: array
            validation_mode:
              description: How to validate DNS server configuration
              enum:
                - exact_match
                - exact_with_extra
                - contains
              type: string
            warn:
              description: Warn users if requirement is not configured properly
              type: boolean
            block:
              description: Block users if requirement is not configured properly
              type: boolean
            goal:
              description: Goal - whether dns should be configured properly
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - dns_servers
            - validation_mode
            - warn
          type: object
        screen_sharing:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if screen sharing is enabled
              type: boolean
            block:
              description: Block users if screen sharing is enabled
              type: boolean
            goal:
              description: Goal - whether screen sharing should be disabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        remote_login:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if remote login is enabled
              type: boolean
            block:
              description: Block users if remote login is enabled
              type: boolean
            goal:
              description: Goal - whether remote login should be disabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        remote_management:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if remote management is enabled
              type: boolean
            block:
              description: Block users if remote management is enabled
              type: boolean
            goal:
              description: Goal - whether remote management should be disabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        remote_scripting:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if remote scripting is enabled
              type: boolean
            block:
              description: Block users if remote scripting is enabled
              type: boolean
            goal:
              description: Goal - whether remote scripting should be disabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        jailbroken:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if device is jailbroken
              type: boolean
            block:
              description: Block users if device is jailbroken
              type: boolean
            goal:
              description: Goal - whether device should not be jailbroken
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        rooted:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if device is rooted
              type: boolean
            block:
              description: Block users if device is rooted
              type: boolean
            goal:
              description: Goal - whether device should not be rooted
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        developer_mode:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if developer mode is enabled
              type: boolean
            block:
              description: Block users if developer mode is enabled
              type: boolean
            goal:
              description: Goal - whether developer mode should be disabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        secure_boot:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if secure boot is not enabled
              type: boolean
            block:
              description: Block users if secure boot is not enabled
              type: boolean
            goal:
              description: Goal - whether secure boot should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        integrity_protection:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if integrity protection is not enabled
              type: boolean
            block:
              description: Block users if integrity protection is not enabled
              type: boolean
            goal:
              description: Goal - whether integrity protection should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        find_my_device:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if find my device is enabled
              type: boolean
            block:
              description: Block users if find my device is enabled
              type: boolean
            goal:
              description: Goal - whether find my device should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        vanta:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if vanta is not enabled
              type: boolean
            block:
              description: Block users if vanta is not enabled
              type: boolean
            goal:
              description: Goal - whether vanta should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        intune:
          example:
            warn: true
            goal: true
            external_enrollment_allowed: true
            escalation:
              mode: grace_days
              block_after_days: 1
            tenant_ids:
              - tenant_ids
              - tenant_ids
            block: true
          properties:
            tenant_ids:
              description: List of allowed Intune tenant IDs
              items:
                type: string
              type: array
            external_enrollment_allowed:
              description: Allow devices to be enrolled with an external organisation
              type: boolean
            warn:
              description: Warn users if intune is not enabled
              type: boolean
            block:
              description: Block users if intune is not enabled
              type: boolean
            goal:
              description: Goal - whether intune should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - tenant_ids
            - warn
          type: object
        aikido_safe_chain:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if Aikido Safe Chain is not installed and active
              type: boolean
            block:
              description: Block users if Aikido Safe Chain is not installed and active
              type: boolean
            goal:
              description: Goal - whether Aikido Safe Chain should be installed and active
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        aikido_endpoint:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
            endpoint_token: endpoint_token
          properties:
            endpoint_token:
              description: Aikido Endpoint registration token used for self-installation and tenant association
              type: string
            warn:
              description: Warn users if Aikido Endpoint is not installed and active
              type: boolean
            block:
              description: Block users if Aikido Endpoint is not installed and active
              type: boolean
            goal:
              description: Goal - whether Aikido Endpoint should be installed and active
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        secrets_in_environment:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if secrets are detected in environment
              type: boolean
            block:
              description: Block users if secrets are detected in environment
              type: boolean
            goal:
              description: Goal - whether secrets should not be in environment
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        autonomous_agents_present:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if autonomous agents are present
              type: boolean
            block:
              description: Block users if autonomous agents are present
              type: boolean
            goal:
              description: Goal - whether autonomous agents should not be present
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        unsafe_ai_mode:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if unsafe AI configurations are detected
              type: boolean
            block:
              description: Block users if unsafe AI configurations are detected
              type: boolean
            goal:
              description: Goal - whether unsafe AI configurations should not be present
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        unguarded_elevation:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if unguarded elevation is detected
              type: boolean
            block:
              description: Block users if unguarded elevation is detected
              type: boolean
            goal:
              description: Goal - whether unguarded elevation should not be present
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        chrome_safebrowsing_enabled:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if Chrome Safe Browsing is not enabled
              type: boolean
            block:
              description: Block users if Chrome Safe Browsing is not enabled
              type: boolean
            goal:
              description: Goal - whether Chrome Safe Browsing should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        chrome_safebrowsing_enhanced:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if Chrome Enhanced Safe Browsing is not enabled
              type: boolean
            block:
              description: Block users if Chrome Enhanced Safe Browsing is not enabled
              type: boolean
            goal:
              description: Goal - whether Chrome Enhanced Safe Browsing should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        chrome_do_not_track:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if Chrome Do Not Track is not enabled
              type: boolean
            block:
              description: Block users if Chrome Do Not Track is not enabled
              type: boolean
            goal:
              description: Goal - whether Chrome Do Not Track should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        chrome_dns_over_https:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if Chrome DNS over HTTPS is not enabled
              type: boolean
            block:
              description: Block users if Chrome DNS over HTTPS is not enabled
              type: boolean
            goal:
              description: Goal - whether Chrome DNS over HTTPS should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        firefox_https_only:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if Firefox HTTPS-Only mode is not enabled
              type: boolean
            block:
              description: Block users if Firefox HTTPS-Only mode is not enabled
              type: boolean
            goal:
              description: Goal - whether Firefox HTTPS-Only mode should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        firefox_dns_over_https:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if Firefox DNS over HTTPS is not enabled
              type: boolean
            block:
              description: Block users if Firefox DNS over HTTPS is not enabled
              type: boolean
            goal:
              description: Goal - whether Firefox DNS over HTTPS should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        firefox_enhanced_tracking_protection:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if Firefox Enhanced Tracking Protection is not enabled
              type: boolean
            block:
              description: Block users if Firefox Enhanced Tracking Protection is not enabled
              type: boolean
            goal:
              description: Goal - whether Firefox Enhanced Tracking Protection should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        firefox_enhanced_tracking_protection_strict:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if Firefox Enhanced Tracking Protection strict mode is not enabled
              type: boolean
            block:
              description: Block users if Firefox Enhanced Tracking Protection strict mode is not enabled
              type: boolean
            goal:
              description: Goal - whether Firefox Enhanced Tracking Protection strict mode should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        unattended_remote_access:
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if unattended remote access tools are configured
              type: boolean
            block:
              description: Block users if unattended remote access tools are configured
              type: boolean
            goal:
              description: Goal - whether unattended remote access tools should not be configured
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        install_protection:
          description: 'Policy for the OS-level install protection guardrail (Gatekeeper on macOS, SmartScreen / Defender PUA on Windows).'
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if install protection is not enabled
              type: boolean
            block:
              description: Block users if install protection is not enabled
              type: boolean
            goal:
              description: Goal - whether install protection should be enabled
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_revoked_signature_apps:
          description: Policy for apps whose code-signing certificate has been revoked by the OS.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if apps with revoked signatures are present
              type: boolean
            block:
              description: Block users if apps with revoked signatures are present
              type: boolean
            goal:
              description: Goal - whether apps with revoked signatures should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_tampered_apps:
          description: Policy for apps whose binary does not match its code signature.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if tampered apps are present
              type: boolean
            block:
              description: Block users if tampered apps are present
              type: boolean
            goal:
              description: Goal - whether tampered apps should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_untrusted_signer_apps:
          description: Policy for apps signed by an untrusted or unknown developer.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if apps from untrusted signers are present
              type: boolean
            block:
              description: Block users if apps from untrusted signers are present
              type: boolean
            goal:
              description: Goal - whether apps from untrusted signers should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_unsigned_apps:
          description: Policy for apps that carry no code signature at all.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if unsigned apps are present
              type: boolean
            block:
              description: Block users if unsigned apps are present
              type: boolean
            goal:
              description: Goal - whether unsigned apps should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_adhoc_signed_apps:
          description: Policy for apps that carry only an ad-hoc (self-issued) signature.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if ad-hoc signed apps are present
              type: boolean
            block:
              description: Block users if ad-hoc signed apps are present
              type: boolean
            goal:
              description: Goal - whether ad-hoc signed apps should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_unnotarized_apps:
          description: Policy for macOS apps signed with a Developer ID but without Apple notarization.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if apps without notarization are present
              type: boolean
            block:
              description: Block users if apps without notarization are present
              type: boolean
            goal:
              description: Goal - whether apps without notarization should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_cryptominers:
          description: Policy for cryptominer applications.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if cryptominer applications are present
              type: boolean
            block:
              description: Block users if cryptominer applications are present
              type: boolean
            goal:
              description: Goal - whether cryptominer applications should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_hacking_pentest:
          description: Policy for hacking and pentest tools.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if hacking and pentest tools are present
              type: boolean
            block:
              description: Block users if hacking and pentest tools are present
              type: boolean
            goal:
              description: Goal - whether hacking and pentest tools should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_piracy_p2p:
          description: Policy for piracy and peer-to-peer applications.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if piracy and P2P applications are present
              type: boolean
            block:
              description: Block users if piracy and P2P applications are present
              type: boolean
            goal:
              description: Goal - whether piracy and P2P applications should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_jailbreak_rooting:
          description: Policy for jailbreak and rooting tools.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if jailbreak and rooting tools are present
              type: boolean
            block:
              description: Block users if jailbreak and rooting tools are present
              type: boolean
            goal:
              description: Goal - whether jailbreak and rooting tools should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_vpn_clients:
          description: Policy for VPN clients.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if VPN clients are present
              type: boolean
            block:
              description: Block users if VPN clients are present
              type: boolean
            goal:
              description: Goal - whether VPN clients should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_third_party_ai_coding:
          description: Policy for third-party AI coding tools.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if third-party AI coding tools are present
              type: boolean
            block:
              description: Block users if third-party AI coding tools are present
              type: boolean
            goal:
              description: Goal - whether third-party AI coding tools should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_experimental_browsers:
          description: Policy for experimental browsers.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if experimental browsers are present
              type: boolean
            block:
              description: Block users if experimental browsers are present
              type: boolean
            goal:
              description: Goal - whether experimental browsers should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_virtualization:
          description: Policy for virtualization software.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if virtualization software is present
              type: boolean
            block:
              description: Block users if virtualization software is present
              type: boolean
            goal:
              description: Goal - whether virtualization software should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_games:
          description: Policy for games and gaming tools.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if games or gaming tools are present
              type: boolean
            block:
              description: Block users if games or gaming tools are present
              type: boolean
            goal:
              description: Goal - whether games and gaming tools should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
        no_permission_hungry:
          description: Policy for applications that request unusually broad system permissions.
          example:
            warn: true
            goal: true
            escalation:
              mode: grace_days
              block_after_days: 1
            block: true
          properties:
            warn:
              description: Warn users if permission-hungry applications are present
              type: boolean
            block:
              description: Block users if permission-hungry applications are present
              type: boolean
            goal:
              description: Goal - whether permission-hungry applications should be absent
              type: boolean
            escalation:
              $ref: '#/components/schemas/CheckEscalation'
          required:
            - block
            - warn
          type: object
      required:
        - name
        - organization_id
        - policy_id
      type: object
    CheckEscalation:
      example:
        mode: grace_days
        block_after_days: 1
      properties:
        mode:
          enum:
            - grace_days
          type: string
        block_after_days:
          minimum: 1
          type: integer
      required:
        - mode
      type: object
    SkipLimit:
      properties:
        max_skips:
          minimum: 1
          type: integer
      required:
        - max_skips
      type: object
    AntivirusPolicy:
      example:
        warn: true
        requirements:
          linux:
            allowed_products: []
          windows:
            allowed_products: []
          macos:
            allowed_products: []
        goal: true
        escalation:
          mode: grace_days
          block_after_days: 1
        block: true
      properties:
        warn:
          description: Warn users if antivirus is not enabled
          type: boolean
        block:
          description: Block users if antivirus is not enabled
          type: boolean
        goal:
          description: Goal - whether antivirus should be enabled
          type: boolean
        requirements:
          $ref: '#/components/schemas/AntivirusRequirements'
        escalation:
          $ref: '#/components/schemas/CheckEscalation'
      required:
        - block
        - warn
      type: object
    AntivirusRequirements:
      description: Missing requirements preserve stored rules on update; null clears all rules. Missing OS fields preserve their rule; null clears it.
      example:
        linux:
          allowed_products: []
        windows:
          allowed_products: []
        macos:
          allowed_products: []
      nullable: true
      properties:
        windows:
          $ref: '#/components/schemas/AntivirusProductRequirement'
        linux:
          $ref: '#/components/schemas/AntivirusProductRequirement'
        macos:
          $ref: '#/components/schemas/AntivirusProductRequirement'
      type: object
    AntivirusProductRequirement:
      example:
        allowed_products: []
      nullable: true
      properties:
        allowed_products:
          description: One healthy listed product suffices. An empty list allows any supported healthy product. Windows accepts microsoft_defender or wsc followed by a colon and a normalized full registration name; Linux accepts clamav or microsoft_defender_endpoint; macOS accepts apple_xprotect.
          example: []
          items:
            maxLength: 260
            minLength: 1
            type: string
          maxItems: 16
          type: array
          uniqueItems: true
          x-oapi-codegen-extra-tags:
            dynamodbav: allowedProducts
      required:
        - allowed_products
      type: object
    AntivirusProduct:
      properties:
        product_id:
          maxLength: 260
          minLength: 1
          type: string
        product_name:
          maxLength: 256
          minLength: 1
          type: string
        installed:
          nullable: true
          type: boolean
          x-omitempty: true
        running:
          nullable: true
          type: boolean
          x-omitempty: true
        up_to_date:
          nullable: true
          type: boolean
          x-omitempty: true
        enabled:
          description: Existing XProtect verdict on macOS only.
          nullable: true
          type: boolean
          x-omitempty: true
      required:
        - product_id
        - product_name
      type: object
    PolicyThresholdTimeOption:
      description: Optional dropdown option for policy threshold timing. Missing means the client should use legacy goal-relative fallback.
      enum:
        - direct
      example: direct
      type: string
    VersionPolicy:
      example:
        WarnTime: 1
        BlockTimeOption: direct
        GoalTime: 5
        older_supported_major_versions:
          dont_warn: true
          dont_block: true
        BlockTime: 5
        WarnTimeOption: direct
        beta_versions:
          dont_warn: true
          dont_block: true
      properties:
        WarnTime:
          description: Warn users if their version is older than this many seconds
          type: integer
        WarnTimeOption:
          $ref: '#/components/schemas/PolicyThresholdTimeOption'
        BlockTime:
          description: Block users if their version is older than this many seconds
          type: integer
        BlockTimeOption:
          $ref: '#/components/schemas/PolicyThresholdTimeOption'
        GoalTime:
          description: Goal - time in seconds that devices are allowed to be outdated with security updates
          type: integer
        older_supported_major_versions:
          $ref: '#/components/schemas/MajorVersionsPolicy'
        beta_versions:
          $ref: '#/components/schemas/BetaVersionsPolicy'
      type: object
    VersionPolicyInDays:
      example:
        GoalTimeInDays: 6
        BlockTimeOption: direct
        older_supported_major_versions:
          dont_warn: true
          dont_block: true
        WarnTimeInDays: 1
        BlockTimeInDays: 2
        WarnTimeOption: direct
        beta_versions:
          dont_warn: true
          dont_block: true
      properties:
        WarnTimeInDays:
          description: Warn users if their version is older than this many days
          type: integer
        WarnTimeOption:
          $ref: '#/components/schemas/PolicyThresholdTimeOption'
        BlockTimeInDays:
          description: Block users if their version is older than this many days
          type: integer
        BlockTimeOption:
          $ref: '#/components/schemas/PolicyThresholdTimeOption'
        GoalTimeInDays:
          description: Goal - days that devices are allowed to be outdated with security updates
          type: integer
        older_supported_major_versions:
          $ref: '#/components/schemas/MajorVersionsPolicy'
        beta_versions:
          $ref: '#/components/schemas/BetaVersionsPolicy'
      type: object
    MajorVersionsPolicy:
      example:
        dont_warn: true
        dont_block: true
      properties:
        dont_warn:
          description: 'Do not warn users if on older, but supported major version'
          type: boolean
        dont_block:
          description: 'Do not block users if on older, but supported major version'
          type: boolean
      required:
        - dont_block
        - dont_warn
      type: object
    BetaVersionsPolicy:
      example:
        dont_warn: true
        dont_block: true
      properties:
        dont_warn:
          description: Do not warn users if on beta version
          type: boolean
        dont_block:
          description: Do not block users if on beta version
          type: boolean
      required:
        - dont_block
        - dont_warn
      type: object
    ResendInvitationRequest:
      type: object
      properties:
        organization_id:
          type: string
          description: ID of the organization
        email:
          type: string
          description: Email of the user
        send_email:
          type: boolean
          description: Whether to send an email invitation. Defaults to true.
        send_slack_message:
          type: boolean
          description: Whether to send a Slack invitation message. Defaults to false.
        send_teams_message:
          type: boolean
          description: Whether to send a Microsoft Teams invitation message. Defaults to false.
      required:
        - organization_id
        - email
    Role:
      type: object
      properties:
        email:
          type: string
          description: Email of user
        roleID:
          type: string
          description: ID of Role
        roleType:
          type: string
          description: Type of Role
        organization_id:
          type: string
          description: ID of Organization
        organization_name:
          type: string
          description: Name of Organization
        organization:
          $ref: '#/components/schemas/Organization'
        intercom_hmac:
          type: string
          description: Intercom HMAC
      required:
        - email
        - roleID
        - roleType
        - organization_id
        - organization_name
        - organization
        - intercom_hmac
    RoleList:
      type: array
      items:
        $ref: '#/components/schemas/Role'
    SAMLConfiguration:
      type: object
      properties:
        enabled:
          type: boolean
          description: Indicates if SAML is enabled
        service_provider_assertion_consumer_service_url:
          type: string
          description: URL for the service provider's assertion consumer service
        identity_provider_sso_url:
          type: string
          description: URL for the identity provider's SSO
        identity_provider_issuer:
          type: string
          description: Issuer for the identity provider
        identity_provider_public_certificate:
          type: string
          description: Public certificate for the identity provider
        sign_response:
          type: boolean
          description: Indicates if the response should be signed
        factor_only:
          type: boolean
          description: Indicates if only factor authentication is used
        factor_only_audience:
          type: string
          description: Audience for factor-only authentication
        force_reauthentication:
          type: boolean
          description: Indicates if reauthentication is forced
        prevent_passive_login:
          type: boolean
          description: Indicates if passive login is prevented
        azure_force_account_chooser:
          type: boolean
          description: Indicates if Azure account chooser is forced
        google_force_account_chooser:
          type: boolean
          description: Indicates if Google account chooser is forced
        service_provider_signing_certificate:
          type: string
          description: Service provider's signing certificate (PEM) used to verify signed SP requests
        service_provider_entity_id:
          type: string
          description: Service provider's entity ID used to verify signed SP requests
      required:
        - enabled
        - service_provider_assertion_consumer_service_url
        - identity_provider_sso_url
        - identity_provider_issuer
        - identity_provider_public_certificate
        - sign_response
    Settings:
      type: object
      properties:
        organization_id:
          type: string
          description: ID of the organization
        insight_price:
          type: number
          format: float
          description: Price for insight
        connect_price:
          type: number
          format: float
          description: Price for connect
        free_devices:
          type: integer
          description: Number of free devices
        trial_end_date:
          type: string
          format: date
          description: End date of the trial period
        per_user_price:
          type: number
          format: float
          description: Price per user
        blocked_access:
          type: boolean
          description: Whether access is blocked
    Shadow:
      allOf:
        - $ref: '#/components/schemas/Device'
        - properties:
            browser_user_agent:
              type: string
              description: User agent of the browser
            email:
              type: string
              description: Email associated with the device
            organization_id:
              type: string
              description: ID of the organization
            timestamp_discovered:
              type: integer
              description: Timestamp when the device was discovered
            uuid:
              type: string
              description: UUID of the device
            note:
              type: string
              description: Note added to the device/shadow
            tags:
              type: array
              items:
                type: string
              description: Tags associated with the device/shadow
            snoozed_until:
              type: integer
              format: int64
              description: Absolute timestamp when the device stops being snoozed
            snoozed_at:
              type: integer
              format: int64
              description: Timestamp when snoozing started
            snoozed_by:
              type: string
              description: Email address of the admin who snoozed the device
            snooze_reason:
              type: string
              description: Optional reason for the snooze
            snooze_mfa:
              type: boolean
              description: Whether MFA prompts are also snoozed
            admin_mfa_approval:
              $ref: '#/components/schemas/AdminMfaApprovalDeviceDetail'
              description: Administrators-only approval detail. Server-side omitted for ReadOnly callers and list responses.
    AgentAdoption:
      type: object
      description: 'One day''s snapshot of XFA agent adoption across the whole fleet, independent of any organization. Computed from the organization-independent shadows, so a device belonging to several organizations is counted once.'
      properties:
        date:
          type: string
          description: 'Day the aggregate was produced, as YYYY-MM-DD'
          example: '2026-08-24'
        windowDays:
          type: integer
          description: How far back a device must have submitted to be counted
          example: 30
        generatedAt:
          type: integer
          format: int64
          description: Unix timestamp (seconds) the aggregate was written
        desktop:
          $ref: '#/components/schemas/AgentAdoptionPlatform'
        mobile:
          $ref: '#/components/schemas/AgentAdoptionPlatform'
        other:
          $ref: '#/components/schemas/AgentAdoptionPlatform'
      required:
        - date
        - windowDays
        - generatedAt
        - desktop
        - mobile
        - other
    AgentAdoptionPlatform:
      type: object
      description: 'Counts for one platform grouping. Skipped and unsupported devices cannot run the agent, so they are carved out of the denominator: adoptable = total - skipped - unsupported, and adoptable = withAgent + agentless + withoutAgent.'
      properties:
        total:
          type: integer
          description: Full active population for this platform
        adoptable:
          type: integer
          description: Devices that could run the agent (total minus skipped and unsupported)
        skipped:
          type: integer
          description: Devices whose user chose to skip the check
        unsupported:
          type: integer
          description: Devices XFA does not support
        withAgent:
          type: integer
          description: Devices reporting a real agent version
        agentless:
          type: integer
          description: Devices reporting the agentless sentinel
        withoutAgent:
          type: integer
          description: 'Adoptable devices reporting no version, i.e. browser flow only'
        nativeClient:
          type: integer
          description: Devices reporting the native client as installed
        versions:
          type: object
          additionalProperties:
            type: integer
          description: 'Agent version to device count, over withAgent devices only. Prerelease build metadata is collapsed and the optional v prefix is stripped.'
          example:
            2.4.2: 120
            2.4.1: 15
        byOs:
          type: object
          additionalProperties:
            $ref: '#/components/schemas/AgentAdoptionOS'
          description: The same counts broken down per operating system
      required:
        - total
        - adoptable
        - skipped
        - unsupported
        - withAgent
        - agentless
        - withoutAgent
        - nativeClient
    AgentAdoptionOS:
      type: object
      description: The per-operating-system slice of a platform grouping
      properties:
        total:
          type: integer
        adoptable:
          type: integer
        withAgent:
          type: integer
        agentless:
          type: integer
        versions:
          type: object
          additionalProperties:
            type: integer
      required:
        - total
        - adoptable
        - withAgent
        - agentless
    ShadowSnapshot:
      type: object
      properties:
        organizationId:
          type: string
          description: ID of the organization
        policyId:
          type: string
          description: ID of the policy
        windows:
          $ref: '#/components/schemas/EvaluationSummary'
          description: Evaluation summary for Windows devices
        macOs:
          $ref: '#/components/schemas/EvaluationSummary'
          description: Evaluation summary for macOS devices
        linux:
          $ref: '#/components/schemas/EvaluationSummary'
          description: Evaluation summary for Linux devices
        android:
          $ref: '#/components/schemas/EvaluationSummary'
          description: Evaluation summary for Android devices
        ios:
          $ref: '#/components/schemas/EvaluationSummary'
          description: Evaluation summary for iOS devices
        ipadOS:
          $ref: '#/components/schemas/EvaluationSummary'
          description: Evaluation summary for iPadOS devices
        cves:
          description: CVE summary information
          type: object
          properties:
            nonEncryptedCount:
              type: integer
              description: Number of systems without encryption
            outOfDateOSCount:
              type: integer
              description: Number of systems running an out-of-date OS
            outOfDateBrowserCount:
              type: integer
              description: Number of systems with outdated browsers
            ransomwareCVEs:
              type: object
              additionalProperties:
                type: integer
              description: Map of ransomware CVE identifiers to their counts
              nullable: true
            phishingCVEs:
              type: object
              additionalProperties:
                type: integer
              description: Map of phishing CVE identifiers to their counts
              nullable: true
            dataBreachCVEs:
              type: object
              additionalProperties:
                type: integer
              description: Map of data breach CVE identifiers to their counts
              nullable: true
            vulnerableDeviceCount:
              type: integer
              description: Number of devices with vulnerabilities
            ransomwareUniqueDeviceCount:
              type: integer
              description: Number of unique devices with ransomware vulnerabilities
            phishingUniqueDeviceCount:
              type: integer
              description: Number of unique devices with phishing vulnerabilities
            dataBreachUniqueDeviceCount:
              type: integer
              description: Number of unique devices with data breach vulnerabilities
          required:
            - nonEncryptedCount
            - outOfDateOSCount
            - outOfDateBrowserCount
            - vulnerableDeviceCount
            - ransomwareUniqueDeviceCount
            - phishingUniqueDeviceCount
            - dataBreachUniqueDeviceCount
        discoveredDevices:
          type: integer
          description: Number of discovered devices
        managedDevices:
          type: integer
          description: Number of managed devices
        unverifiedDevices:
          type: integer
          description: Number of unverified devices
        itemType:
          type: string
          description: Type of the item (shadow-snapshot)
        timestampSubmitted:
          type: integer
          format: int64
          description: Timestamp when the snapshot was submitted
      required:
        - organizationId
        - policyId
        - windows
        - macOs
        - linux
        - android
        - ios
        - ipadOS
        - discoveredDevices
        - managedDevices
        - itemType
        - timestampSubmitted
        - uuid
    Snapshot:
      type: object
      properties:
        organization_id:
          type: string
          description: ID of the organization
        target_date_unix:
          type: integer
          format: int64
          description: Target date in Unix timestamp
        target_date_end_unix:
          type: integer
          format: int64
          description: End of target date in Unix timestamp
        number_devices_total:
          type: integer
          description: Total number of devices
        os_check_supported_all:
          type: integer
          description: Number of devices that have the OS check supported (all operating systems)
        os_check_supported_windows:
          type: integer
          description: Number of devices that have the OS check supported and are Windows
        os_check_supported_macos:
          type: integer
          description: Number of devices that have the OS check supported and are macOS
        os_check_supported_linux:
          type: integer
          description: Number of devices that have the OS check supported and are Linux
        os_check_supported_ios:
          type: integer
          description: Number of devices that have the OS check supported and are iOS
        os_check_supported_ipados:
          type: integer
          description: Number of devices that have the OS check supported and are iPadOS
        os_check_supported_android:
          type: integer
          description: Number of devices that have the OS check supported and are Android
        os_check_supported_other:
          type: integer
          description: Number of devices that have the OS check supported and are other
        os_check_known_all:
          type: integer
          description: Number of devices that have the OS check known (all operating systems)
        os_check_known_windows:
          type: integer
          description: Number of devices that have the OS check known and are Windows
        os_check_known_macos:
          type: integer
          description: Number of devices that have the OS check known and are macOS
        os_check_known_linux:
          type: integer
          description: Number of devices that have the OS check known and are Linux
        os_check_known_ios:
          type: integer
          description: Number of devices that have the OS check known and are iOS
        os_check_known_ipados:
          type: integer
          description: Number of devices that have the OS check known and are iPadOS
        os_check_known_android:
          type: integer
          description: Number of devices that have the OS check known and are Android
        os_check_known_other:
          type: integer
          description: Number of devices that have the OS check known and are other
        os_p0_days_outdated_when_only_stable_allowed_all:
          type: number
          format: float
          description: p0 days outdated when only stable is allowed for all devices
        os_p0_days_outdated_when_only_stable_allowed_windows:
          type: number
          format: float
          description: p0 days outdated when only stable is allowed for Windows devices
        os_p0_days_outdated_when_only_stable_allowed_macos:
          type: number
          format: float
          description: p0 days outdated when only stable is allowed for macOS devices
        os_p0_days_outdated_when_only_stable_allowed_linux:
          type: number
          format: float
          description: p0 days outdated when only stable is allowed for Linux devices
        os_p0_days_outdated_when_only_stable_allowed_ios:
          type: number
          format: float
          description: p0 days outdated when only stable is allowed for iOS devices
        os_p0_days_outdated_when_only_stable_allowed_ipados:
          type: number
          format: float
          description: p0 days outdated when only stable is allowed for iPadOS devices
        os_p0_days_outdated_when_only_stable_allowed_android:
          type: number
          format: float
          description: p0 days outdated when only stable is allowed for Android devices
        os_p0_days_outdated_when_only_stable_allowed_other:
          type: number
          format: float
          description: p0 days outdated when only stable is allowed for Other devices
        os_p5_days_outdated_when_only_stable_allowed_all:
          type: number
          format: float
          description: p5 days outdated when only stable is allowed for all devices
        os_p5_days_outdated_when_only_stable_allowed_windows:
          type: number
          format: float
          description: p5 days outdated when only stable is allowed for Windows devices
        os_p5_days_outdated_when_only_stable_allowed_macos:
          type: number
          format: float
          description: p5 days outdated when only stable is allowed for macOS devices
        os_p5_days_outdated_when_only_stable_allowed_linux:
          type: number
          format: float
          description: p5 days outdated when only stable is allowed for Linux devices
        os_p5_days_outdated_when_only_stable_allowed_ios:
          type: number
          format: float
          description: p5 days outdated when only stable is allowed for iOS devices
        os_p5_days_outdated_when_only_stable_allowed_ipados:
          type: number
          format: float
          description: p5 days outdated when only stable is allowed for iPadOS devices
        os_p5_days_outdated_when_only_stable_allowed_android:
          type: number
          format: float
          description: p5 days outdated when only stable is allowed for Android devices
        os_p5_days_outdated_when_only_stable_allowed_other:
          type: number
          format: float
          description: p5 days outdated when only stable is allowed for Other devices
        os_p25_days_outdated_when_only_stable_allowed_all:
          type: number
          format: float
          description: p25 days outdated when only stable is allowed for all devices
        os_p25_days_outdated_when_only_stable_allowed_windows:
          type: number
          format: float
          description: p25 days outdated when only stable is allowed for Windows devices
        os_p25_days_outdated_when_only_stable_allowed_macos:
          type: number
          format: float
          description: p25 days outdated when only stable is allowed for macOS devices
        os_p25_days_outdated_when_only_stable_allowed_linux:
          type: number
          format: float
          description: p25 days outdated when only stable is allowed for Linux devices
        os_p25_days_outdated_when_only_stable_allowed_ios:
          type: number
          format: float
          description: p25 days outdated when only stable is allowed for iOS devices
        os_p25_days_outdated_when_only_stable_allowed_ipados:
          type: number
          format: float
          description: p25 days outdated when only stable is allowed for iPadOS devices
        os_p25_days_outdated_when_only_stable_allowed_android:
          type: number
          format: float
          description: p25 days outdated when only stable is allowed for Android devices
        os_p25_days_outdated_when_only_stable_allowed_other:
          type: number
          format: float
          description: p25 days outdated when only stable is allowed for other devices
        os_p50_days_outdated_when_only_stable_allowed_all:
          type: number
          format: float
          description: median days outdated when only stable is allowed for all devices
        os_p50_days_outdated_when_only_stable_allowed_windows:
          type: number
          format: float
          description: median days outdated when only stable is allowed for Windows devices
        os_p50_days_outdated_when_only_stable_allowed_macos:
          type: number
          format: float
          description: median days outdated when only stable is allowed for macOS devices
        os_p50_days_outdated_when_only_stable_allowed_linux:
          type: number
          format: float
          description: median days outdated when only stable is allowed for Linux devices
        os_p50_days_outdated_when_only_stable_allowed_ios:
          type: number
          format: float
          description: median days outdated when only stable is allowed for iOS devices
        os_p50_days_outdated_when_only_stable_allowed_ipados:
          type: number
          format: float
          description: median days outdated when only stable is allowed for iPadOS devices
        os_p50_days_outdated_when_only_stable_allowed_android:
          type: number
          format: float
          description: median days outdated when only stable is allowed for Android devices
        os_p50_days_outdated_when_only_stable_allowed_other:
          type: number
          format: float
          description: median days outdated when only stable is allowed for Other devices
        os_p75_days_outdated_when_only_stable_allowed_all:
          type: number
          format: float
          description: p75 days outdated when only stable is allowed for all devices
        os_p75_days_outdated_when_only_stable_allowed_windows:
          type: number
          format: float
          description: p75 days outdated when only stable is allowed for Windows devices
        os_p75_days_outdated_when_only_stable_allowed_macos:
          type: number
          format: float
          description: p75 days outdated when only stable is allowed for macOS devices
        os_p75_days_outdated_when_only_stable_allowed_linux:
          type: number
          format: float
          description: p75 days outdated when only stable is allowed for Linux devices
        os_p75_days_outdated_when_only_stable_allowed_ios:
          type: number
          format: float
          description: p75 days outdated when only stable is allowed for iOS devices
        os_p75_days_outdated_when_only_stable_allowed_ipados:
          type: number
          format: float
          description: p75 days outdated when only stable is allowed for iPadOS devices
        os_p75_days_outdated_when_only_stable_allowed_android:
          type: number
          format: float
          description: p75 days outdated when only stable is allowed for Android devices
        os_p75_days_outdated_when_only_stable_allowed_other:
          type: number
          format: float
          description: p75 days outdated when only stable is allowed for Other devices
        os_p95_days_outdated_when_only_stable_allowed_all:
          type: number
          format: float
          description: p95 days outdated when only stable is allowed for all devices
        os_p95_days_outdated_when_only_stable_allowed_windows:
          type: number
          format: float
          description: p95 days outdated when only stable is allowed for Windows devices
        os_p95_days_outdated_when_only_stable_allowed_macos:
          type: number
          format: float
          description: p95 days outdated when only stable is allowed for macOS devices
        os_p95_days_outdated_when_only_stable_allowed_linux:
          type: number
          format: float
          description: p95 days outdated when only stable is allowed for Linux devices
        os_p95_days_outdated_when_only_stable_allowed_ios:
          type: number
          format: float
          description: p95 days outdated when only stable is allowed for iOS devices
        os_p95_days_outdated_when_only_stable_allowed_ipados:
          type: number
          format: float
          description: p95 days outdated when only stable is allowed for iPadOS devices
        os_p95_days_outdated_when_only_stable_allowed_android:
          type: number
          format: float
          description: p95 days outdated when only stable is allowed for Android devices
        os_p95_days_outdated_when_only_stable_allowed_other:
          type: number
          format: float
          description: p95 days outdated when only stable is allowed for Other devices
        os_p100_days_outdated_when_only_stable_allowed_all:
          type: number
          format: float
          description: p100 days outdated when only stable is allowed for all devices
        os_p100_days_outdated_when_only_stable_allowed_windows:
          type: number
          format: float
          description: p100 days outdated when only stable is allowed for Windows devices
        os_p100_days_outdated_when_only_stable_allowed_macos:
          type: number
          format: float
          description: p100 days outdated when only stable is allowed for macOS devices
        os_p100_days_outdated_when_only_stable_allowed_linux:
          type: number
          format: float
          description: p100 days outdated when only stable is allowed for Linux devices
        os_p100_days_outdated_when_only_stable_allowed_ios:
          type: number
          format: float
          description: p100 days outdated when only stable is allowed for iOS devices
        os_p100_days_outdated_when_only_stable_allowed_ipados:
          type: number
          format: float
          description: p100 days outdated when only stable is allowed for iPadOS devices
        os_p100_days_outdated_when_only_stable_allowed_android:
          type: number
          format: float
          description: p100 days outdated when only stable is allowed for Android devices
        os_p100_days_outdated_when_only_stable_allowed_other:
          type: number
          format: float
          description: p100 days outdated when only stable is allowed for Other devices
        os_avg_days_outdated_when_only_stable_allowed_all:
          type: number
          format: float
          description: average days outdated when only stable is allowed for all devices
        os_avg_days_outdated_when_only_stable_allowed_windows:
          type: number
          format: float
          description: average days outdated when only stable is allowed for Windows devices
        os_avg_days_outdated_when_only_stable_allowed_macos:
          type: number
          format: float
          description: average days outdated when only stable is allowed for macOS devices
        os_avg_days_outdated_when_only_stable_allowed_linux:
          type: number
          format: float
          description: average days outdated when only stable is allowed for Linux devices
        os_avg_days_outdated_when_only_stable_allowed_ios:
          type: number
          format: float
          description: average days outdated when only stable is allowed for iOS devices
        os_avg_days_outdated_when_only_stable_allowed_ipados:
          type: number
          format: float
          description: average days outdated when only stable is allowed for iPadOS devices
        os_avg_days_outdated_when_only_stable_allowed_android:
          type: number
          format: float
          description: average days outdated when only stable is allowed for Android devices
        os_avg_days_outdated_when_only_stable_allowed_other:
          type: number
          format: float
          description: average days outdated when only stable is allowed for Other devices
        os_p0_days_outdated_when_stable_and_beta_allowed_all:
          type: number
          format: float
          description: p0 days outdated when stable and beta are allowed for all devices
        os_p0_days_outdated_when_stable_and_beta_allowed_windows:
          type: number
          format: float
          description: p0 days outdated when stable and beta are allowed for Windows devices
        os_p0_days_outdated_when_stable_and_beta_allowed_macos:
          type: number
          format: float
          description: p0 days outdated when stable and beta are allowed for macOS devices
        os_p0_days_outdated_when_stable_and_beta_allowed_linux:
          type: number
          format: float
          description: p0 days outdated when stable and beta are allowed for Linux devices
        os_p0_days_outdated_when_stable_and_beta_allowed_ios:
          type: number
          format: float
          description: p0 days outdated when stable and beta are allowed for iOS devices
        os_p0_days_outdated_when_stable_and_beta_allowed_ipados:
          type: number
          format: float
          description: p0 days outdated when stable and beta are allowed for iPadOS devices
        os_p0_days_outdated_when_stable_and_beta_allowed_android:
          type: number
          format: float
          description: p0 days outdated when stable and beta are allowed for Android devices
        os_p0_days_outdated_when_stable_and_beta_allowed_other:
          type: number
          format: float
          description: p0 days outdated when stable and beta are allowed for Other devices
        os_p5_days_outdated_when_stable_and_beta_allowed_all:
          type: number
          format: float
          description: p5 days outdated when stable and beta are allowed for all devices
        os_p5_days_outdated_when_stable_and_beta_allowed_windows:
          type: number
          format: float
          description: p5 days outdated when stable and beta are allowed for Windows devices
        os_p5_days_outdated_when_stable_and_beta_allowed_macos:
          type: number
          format: float
          description: p5 days outdated when stable and beta are allowed for macOS devices
        os_p5_days_outdated_when_stable_and_beta_allowed_linux:
          type: number
          format: float
          description: p5 days outdated when stable and beta are allowed for Linux devices
        os_p5_days_outdated_when_stable_and_beta_allowed_ios:
          type: number
          format: float
          description: p5 days outdated when stable and beta are allowed for iOS devices
        os_p5_days_outdated_when_stable_and_beta_allowed_ipados:
          type: number
          format: float
          description: p5 days outdated when stable and beta are allowed for iPadOS devices
        os_p5_days_outdated_when_stable_and_beta_allowed_android:
          type: number
          format: float
          description: p5 days outdated when stable and beta are allowed for Android devices
        os_p5_days_outdated_when_stable_and_beta_allowed_other:
          type: number
          format: float
          description: p5 days outdated when stable and beta are allowed for Other devices
        os_p25_days_outdated_when_stable_and_beta_allowed_all:
          type: number
          format: float
          description: p25 days outdated when stable and beta are allowed for all devices
        os_p25_days_outdated_when_stable_and_beta_allowed_windows:
          type: number
          format: float
          description: p25 days outdated when stable and beta are allowed for Windows devices
        os_p25_days_outdated_when_stable_and_beta_allowed_macos:
          type: number
          format: float
          description: p25 days outdated when stable and beta are allowed for macOS devices
        os_p25_days_outdated_when_stable_and_beta_allowed_linux:
          type: number
          format: float
          description: p25 days outdated when stable and beta are allowed for Linux devices
        os_p25_days_outdated_when_stable_and_beta_allowed_ios:
          type: number
          format: float
          description: p25 days outdated when stable and beta are allowed for iOS devices
        os_p25_days_outdated_when_stable_and_beta_allowed_ipados:
          type: number
          format: float
          description: p25 days outdated when stable and beta are allowed for iPadOS devices
        os_p25_days_outdated_when_stable_and_beta_allowed_android:
          type: number
          format: float
          description: p25 days outdated when stable and beta are allowed for Android devices
        os_p25_days_outdated_when_stable_and_beta_allowed_other:
          type: number
          format: float
          description: p25 days outdated when stable and beta are allowed for other devices
        os_p50_days_outdated_when_stable_and_beta_allowed_all:
          type: number
          format: float
          description: median days outdated when stable and beta are allowed for all devices
        os_p50_days_outdated_when_stable_and_beta_allowed_windows:
          type: number
          format: float
          description: median days outdated when stable and beta are allowed for Windows devices
        os_p50_days_outdated_when_stable_and_beta_allowed_macos:
          type: number
          format: float
          description: median days outdated when stable and beta are allowed for macOS devices
        os_p50_days_outdated_when_stable_and_beta_allowed_linux:
          type: number
          format: float
          description: median days outdated when stable and beta are allowed for Linux devices
        os_p50_days_outdated_when_stable_and_beta_allowed_ios:
          type: number
          format: float
          description: median days outdated when stable and beta are allowed for iOS devices
        os_p50_days_outdated_when_stable_and_beta_allowed_ipados:
          type: number
          format: float
          description: median days outdated when stable and beta are allowed for iPadOS devices
        os_p50_days_outdated_when_stable_and_beta_allowed_android:
          type: number
          format: float
          description: median days outdated when stable and beta are allowed for Android devices
        os_p50_days_outdated_when_stable_and_beta_allowed_other:
          type: number
          format: float
          description: median days outdated when stable and beta are allowed for Other devices
        os_p75_days_outdated_when_stable_and_beta_allowed_all:
          type: number
          format: float
          description: p75 days outdated when stable and beta are allowed for all devices
        os_p75_days_outdated_when_stable_and_beta_allowed_windows:
          type: number
          format: float
          description: p75 days outdated when stable and beta are allowed for Windows devices
        os_p75_days_outdated_when_stable_and_beta_allowed_macos:
          type: number
          format: float
          description: p75 days outdated when stable and beta are allowed for macOS devices
        os_p75_days_outdated_when_stable_and_beta_allowed_linux:
          type: number
          format: float
          description: p75 days outdated when stable and beta are allowed for Linux devices
        os_p75_days_outdated_when_stable_and_beta_allowed_ios:
          type: number
          format: float
          description: p75 days outdated when stable and beta are allowed for iOS devices
        os_p75_days_outdated_when_stable_and_beta_allowed_ipados:
          type: number
          format: float
          description: p75 days outdated when stable and beta are allowed for iPadOS devices
        os_p75_days_outdated_when_stable_and_beta_allowed_android:
          type: number
          format: float
          description: p75 days outdated when stable and beta are allowed for Android devices
        os_p75_days_outdated_when_stable_and_beta_allowed_other:
          type: number
          format: float
          description: p75 days outdated when stable and beta are allowed for Other devices
        os_p95_days_outdated_when_stable_and_beta_allowed_all:
          type: number
          format: float
          description: p95 days outdated when stable and beta are allowed for all devices
        os_p95_days_outdated_when_stable_and_beta_allowed_windows:
          type: number
          format: float
          description: p95 days outdated when stable and beta are allowed for Windows devices
        os_p95_days_outdated_when_stable_and_beta_allowed_macos:
          type: number
          format: float
          description: p95 days outdated when stable and beta are allowed for macOS devices
        os_p95_days_outdated_when_stable_and_beta_allowed_linux:
          type: number
          format: float
          description: p95 days outdated when stable and beta are allowed for Linux devices
        os_p95_days_outdated_when_stable_and_beta_allowed_ios:
          type: number
          format: float
          description: p95 days outdated when stable and beta are allowed for iOS devices
        os_p95_days_outdated_when_stable_and_beta_allowed_ipados:
          type: number
          format: float
          description: p95 days outdated when stable and beta are allowed for iPadOS devices
        os_p95_days_outdated_when_stable_and_beta_allowed_android:
          type: number
          format: float
          description: p95 days outdated when stable and beta are allowed for Android devices
        os_p95_days_outdated_when_stable_and_beta_allowed_other:
          type: number
          format: float
          description: p95 days outdated when stable and beta are allowed for Other devices
        os_p100_days_outdated_when_stable_and_beta_allowed_all:
          type: number
          format: float
          description: p100 days outdated when stable and beta are allowed for all devices
        os_p100_days_outdated_when_stable_and_beta_allowed_windows:
          type: number
          format: float
          description: p100 days outdated when stable and beta are allowed for Windows devices
        os_p100_days_outdated_when_stable_and_beta_allowed_macos:
          type: number
          format: float
          description: p100 days outdated when stable and beta are allowed for macOS devices
        os_p100_days_outdated_when_stable_and_beta_allowed_linux:
          type: number
          format: float
          description: p100 days outdated when stable and beta are allowed for Linux devices
        os_p100_days_outdated_when_stable_and_beta_allowed_ios:
          type: number
          format: float
          description: p100 days outdated when stable and beta are allowed for iOS devices
        os_p100_days_outdated_when_stable_and_beta_allowed_ipados:
          type: number
          format: float
          description: p100 days outdated when stable and beta are allowed for iPadOS devices
        os_p100_days_outdated_when_stable_and_beta_allowed_android:
          type: number
          format: float
          description: p100 days outdated when stable and beta are allowed for Android devices
        os_p100_days_outdated_when_stable_and_beta_allowed_other:
          type: number
          format: float
          description: p100 days outdated when stable and beta are allowed for Other devices
        os_avg_days_outdated_when_stable_and_beta_allowed_all:
          type: number
          format: float
          description: average days outdated when stable and beta are allowed for all devices
        os_avg_days_outdated_when_stable_and_beta_allowed_windows:
          type: number
          format: float
          description: average days outdated when stable and beta are allowed for Windows devices
        os_avg_days_outdated_when_stable_and_beta_allowed_macos:
          type: number
          format: float
          description: average days outdated when stable and beta are allowed for macOS devices
        os_avg_days_outdated_when_stable_and_beta_allowed_linux:
          type: number
          format: float
          description: average days outdated when stable and beta are allowed for Linux devices
        os_avg_days_outdated_when_stable_and_beta_allowed_ios:
          type: number
          format: float
          description: average days outdated when stable and beta are allowed for iOS devices
        os_avg_days_outdated_when_stable_and_beta_allowed_ipados:
          type: number
          format: float
          description: average days outdated when stable and beta are allowed for iPadOS devices
        os_avg_days_outdated_when_stable_and_beta_allowed_android:
          type: number
          format: float
          description: average days outdated when stable and beta are allowed for Android devices
        os_avg_days_outdated_when_stable_and_beta_allowed_other:
          type: number
          format: float
          description: average days outdated when stable and beta are allowed for Other devices
        os_p0_days_outdated_when_all_supported_allowed_all:
          type: number
          format: float
          description: p0 days outdated when all supported are allowed for all devices
        os_p0_days_outdated_when_all_supported_allowed_windows:
          type: number
          format: float
          description: p0 days outdated when all supported are allowed for Windows devices
        os_p0_days_outdated_when_all_supported_allowed_macos:
          type: number
          format: float
          description: p0 days outdated when all supported are allowed for macOS devices
        os_p0_days_outdated_when_all_supported_allowed_linux:
          type: number
          format: float
          description: p0 days outdated when all supported are allowed for Linux devices
        os_p0_days_outdated_when_all_supported_allowed_ios:
          type: number
          format: float
          description: p0 days outdated when all supported are allowed for iOS devices
        os_p0_days_outdated_when_all_supported_allowed_ipados:
          type: number
          format: float
          description: p0 days outdated when all supported are allowed for iPadOS devices
        os_p0_days_outdated_when_all_supported_allowed_android:
          type: number
          format: float
          description: p0 days outdated when all supported are allowed for Android devices
        os_p0_days_outdated_when_all_supported_allowed_other:
          type: number
          format: float
          description: p0 days outdated when all supported are allowed for Other devices
        os_p5_days_outdated_when_all_supported_allowed_all:
          type: number
          format: float
          description: p5 days outdated when all supported are allowed for all devices
        os_p5_days_outdated_when_all_supported_allowed_windows:
          type: number
          format: float
          description: p5 days outdated when all supported are allowed for Windows devices
        os_p5_days_outdated_when_all_supported_allowed_macos:
          type: number
          format: float
          description: p5 days outdated when all supported are allowed for macOS devices
        os_p5_days_outdated_when_all_supported_allowed_linux:
          type: number
          format: float
          description: p5 days outdated when all supported are allowed for Linux devices
        os_p5_days_outdated_when_all_supported_allowed_ios:
          type: number
          format: float
          description: p5 days outdated when all supported are allowed for iOS devices
        os_p5_days_outdated_when_all_supported_allowed_ipados:
          type: number
          format: float
          description: p5 days outdated when all supported are allowed for iPadOS devices
        os_p5_days_outdated_when_all_supported_allowed_android:
          type: number
          format: float
          description: p5 days outdated when all supported are allowed for Android devices
        os_p5_days_outdated_when_all_supported_allowed_other:
          type: number
          format: float
          description: p5 days outdated when all supported are allowed for Other devices
        os_p25_days_outdated_when_all_supported_allowed_all:
          type: number
          format: float
          description: p25 days outdated when all supported are allowed for all devices
        os_p25_days_outdated_when_all_supported_allowed_windows:
          type: number
          format: float
          description: p25 days outdated when all supported are allowed for Windows devices
        os_p25_days_outdated_when_all_supported_allowed_macos:
          type: number
          format: float
          description: p25 days outdated when all supported are allowed for macOS devices
        os_p25_days_outdated_when_all_supported_allowed_linux:
          type: number
          format: float
          description: p25 days outdated when all supported are allowed for Linux devices
        os_p25_days_outdated_when_all_supported_allowed_ios:
          type: number
          format: float
          description: p25 days outdated when all supported are allowed for iOS devices
        os_p25_days_outdated_when_all_supported_allowed_ipados:
          type: number
          format: float
          description: p25 days outdated when all supported are allowed for iPadOS devices
        os_p25_days_outdated_when_all_supported_allowed_android:
          type: number
          format: float
          description: p25 days outdated when all supported are allowed for Android devices
        os_p25_days_outdated_when_all_supported_allowed_other:
          type: number
          format: float
          description: p25 days outdated when all supported are allowed for other devices
        os_p50_days_outdated_when_all_supported_allowed_all:
          type: number
          format: float
          description: median days outdated when all supported are allowed for all devices
        os_p50_days_outdated_when_all_supported_allowed_windows:
          type: number
          format: float
          description: median days outdated when all supported are allowed for Windows devices
        os_p50_days_outdated_when_all_supported_allowed_macos:
          type: number
          format: float
          description: median days outdated when all supported are allowed for macOS devices
        os_p50_days_outdated_when_all_supported_allowed_linux:
          type: number
          format: float
          description: median days outdated when all supported are allowed for Linux devices
        os_p50_days_outdated_when_all_supported_allowed_ios:
          type: number
          format: float
          description: median days outdated when all supported are allowed for iOS devices
        os_p50_days_outdated_when_all_supported_allowed_ipados:
          type: number
          format: float
          description: median days outdated when all supported are allowed for iPadOS devices
        os_p50_days_outdated_when_all_supported_allowed_android:
          type: number
          format: float
          description: median days outdated when all supported are allowed for Android devices
        os_p50_days_outdated_when_all_supported_allowed_other:
          type: number
          format: float
          description: median days outdated when all supported are allowed for Other devices
        os_p75_days_outdated_when_all_supported_allowed_all:
          type: number
          format: float
          description: p75 days outdated when all supported are allowed for all devices
        os_p75_days_outdated_when_all_supported_allowed_windows:
          type: number
          format: float
          description: p75 days outdated when all supported are allowed for Windows devices
        os_p75_days_outdated_when_all_supported_allowed_macos:
          type: number
          format: float
          description: p75 days outdated when all supported are allowed for macOS devices
        os_p75_days_outdated_when_all_supported_allowed_linux:
          type: number
          format: float
          description: p75 days outdated when all supported are allowed for Linux devices
        os_p75_days_outdated_when_all_supported_allowed_ios:
          type: number
          format: float
          description: p75 days outdated when all supported are allowed for iOS devices
        os_p75_days_outdated_when_all_supported_allowed_ipados:
          type: number
          format: float
          description: p75 days outdated when all supported are allowed for iPadOS devices
        os_p75_days_outdated_when_all_supported_allowed_android:
          type: number
          format: float
          description: p75 days outdated when all supported are allowed for Android devices
        os_p75_days_outdated_when_all_supported_allowed_other:
          type: number
          format: float
          description: p75 days outdated when all supported are allowed for Other devices
        os_p95_days_outdated_when_all_supported_allowed_all:
          type: number
          format: float
          description: p95 days outdated when all supported are allowed for all devices
        os_p95_days_outdated_when_all_supported_allowed_windows:
          type: number
          format: float
          description: p95 days outdated when all supported are allowed for Windows devices
        os_p95_days_outdated_when_all_supported_allowed_macos:
          type: number
          format: float
          description: p95 days outdated when all supported are allowed for macOS devices
        os_p95_days_outdated_when_all_supported_allowed_linux:
          type: number
          format: float
          description: p95 days outdated when all supported are allowed for Linux devices
        os_p95_days_outdated_when_all_supported_allowed_ios:
          type: number
          format: float
          description: p95 days outdated when all supported are allowed for iOS devices
        os_p95_days_outdated_when_all_supported_allowed_ipados:
          type: number
          format: float
          description: p95 days outdated when all supported are allowed for iPadOS devices
        os_p95_days_outdated_when_all_supported_allowed_android:
          type: number
          format: float
          description: p95 days outdated when all supported are allowed for Android devices
        os_p95_days_outdated_when_all_supported_allowed_other:
          type: number
          format: float
          description: p95 days outdated when all supported are allowed for Other devices
        os_p100_days_outdated_when_all_supported_allowed_all:
          type: number
          format: float
          description: p100 days outdated when all supported are allowed for all devices
        os_p100_days_outdated_when_all_supported_allowed_windows:
          type: number
          format: float
          description: p100 days outdated when all supported are allowed for Windows devices
        os_p100_days_outdated_when_all_supported_allowed_macos:
          type: number
          format: float
          description: p100 days outdated when all supported are allowed for macOS devices
        os_p100_days_outdated_when_all_supported_allowed_linux:
          type: number
          format: float
          description: p100 days outdated when all supported are allowed for Linux devices
        os_p100_days_outdated_when_all_supported_allowed_ios:
          type: number
          format: float
          description: p100 days outdated when all supported are allowed for iOS devices
        os_p100_days_outdated_when_all_supported_allowed_ipados:
          type: number
          format: float
          description: p100 days outdated when all supported are allowed for iPadOS devices
        os_p100_days_outdated_when_all_supported_allowed_android:
          type: number
          format: float
          description: p100 days outdated when all supported are allowed for Android devices
        os_p100_days_outdated_when_all_supported_allowed_other:
          type: number
          format: float
          description: p100 days outdated when all supported are allowed for Other devices
        os_avg_days_outdated_when_all_supported_allowed_all:
          type: number
          format: float
          description: average days outdated when all supported are allowed for all devices
        os_avg_days_outdated_when_all_supported_allowed_windows:
          type: number
          format: float
          description: average days outdated when all supported are allowed for Windows devices
        os_avg_days_outdated_when_all_supported_allowed_macos:
          type: number
          format: float
          description: average days outdated when all supported are allowed for macOS devices
        os_avg_days_outdated_when_all_supported_allowed_linux:
          type: number
          format: float
          description: average days outdated when all supported are allowed for Linux devices
        os_avg_days_outdated_when_all_supported_allowed_ios:
          type: number
          format: float
          description: average days outdated when all supported are allowed for iOS devices
        os_avg_days_outdated_when_all_supported_allowed_ipados:
          type: number
          format: float
          description: average days outdated when all supported are allowed for iPadOS devices
        os_avg_days_outdated_when_all_supported_allowed_android:
          type: number
          format: float
          description: average days outdated when all supported are allowed for Android devices
        os_avg_days_outdated_when_all_supported_allowed_other:
          type: number
          format: float
          description: average days outdated when all supported are allowed for Other devices
        os_p0_days_outdated_when_all_supported_and_beta_allowed_all:
          type: number
          format: float
          description: p0 days outdated when all supported and beta are allowed for all devices
        os_p0_days_outdated_when_all_supported_and_beta_allowed_windows:
          type: number
          format: float
          description: p0 days outdated when all supported and beta are allowed for Windows devices
        os_p0_days_outdated_when_all_supported_and_beta_allowed_macos:
          type: number
          format: float
          description: p0 days outdated when all supported and beta are allowed for macOS devices
        os_p0_days_outdated_when_all_supported_and_beta_allowed_linux:
          type: number
          format: float
          description: p0 days outdated when all supported and beta are allowed for Linux devices
        os_p0_days_outdated_when_all_supported_and_beta_allowed_ios:
          type: number
          format: float
          description: p0 days outdated when all supported and beta are allowed for iOS devices
        os_p0_days_outdated_when_all_supported_and_beta_allowed_ipados:
          type: number
          format: float
          description: p0 days outdated when all supported and beta are allowed for iPadOS devices
        os_p0_days_outdated_when_all_supported_and_beta_allowed_android:
          type: number
          format: float
          description: p0 days outdated when all supported and beta are allowed for Android devices
        os_p0_days_outdated_when_all_supported_and_beta_allowed_other:
          type: number
          format: float
          description: p0 days outdated when all supported and beta are allowed for Other devices
        os_p5_days_outdated_when_all_supported_and_beta_allowed_all:
          type: number
          format: float
          description: p5 days outdated when all supported and beta are allowed for all devices
        os_p5_days_outdated_when_all_supported_and_beta_allowed_windows:
          type: number
          format: float
          description: p5 days outdated when all supported and beta are allowed for Windows devices
        os_p5_days_outdated_when_all_supported_and_beta_allowed_macos:
          type: number
          format: float
          description: p5 days outdated when all supported and beta are allowed for macOS devices
        os_p5_days_outdated_when_all_supported_and_beta_allowed_linux:
          type: number
          format: float
          description: p5 days outdated when all supported and beta are allowed for Linux devices
        os_p5_days_outdated_when_all_supported_and_beta_allowed_ios:
          type: number
          format: float
          description: p5 days outdated when all supported and beta are allowed for iOS devices
        os_p5_days_outdated_when_all_supported_and_beta_allowed_ipados:
          type: number
          format: float
          description: p5 days outdated when all supported and beta are allowed for iPadOS devices
        os_p5_days_outdated_when_all_supported_and_beta_allowed_android:
          type: number
          format: float
          description: p5 days outdated when all supported and beta are allowed for Android devices
        os_p5_days_outdated_when_all_supported_and_beta_allowed_other:
          type: number
          format: float
          description: p5 days outdated when all supported and beta are allowed for Other devices
        os_p25_days_outdated_when_all_supported_and_beta_allowed_all:
          type: number
          format: float
          description: p25 days outdated when all supported and beta are allowed for all devices
        os_p25_days_outdated_when_all_supported_and_beta_allowed_windows:
          type: number
          format: float
          description: p25 days outdated when all supported and beta are allowed for Windows devices
        os_p25_days_outdated_when_all_supported_and_beta_allowed_macos:
          type: number
          format: float
          description: p25 days outdated when all supported and beta are allowed for macOS devices
        os_p25_days_outdated_when_all_supported_and_beta_allowed_linux:
          type: number
          format: float
          description: p25 days outdated when all supported and beta are allowed for Linux devices
        os_p25_days_outdated_when_all_supported_and_beta_allowed_ios:
          type: number
          format: float
          description: p25 days outdated when all supported and beta are allowed for iOS devices
        os_p25_days_outdated_when_all_supported_and_beta_allowed_ipados:
          type: number
          format: float
          description: p25 days outdated when all supported and beta are allowed for iPadOS devices
        os_p25_days_outdated_when_all_supported_and_beta_allowed_android:
          type: number
          format: float
          description: p25 days outdated when all supported and beta are allowed for Android devices
        os_p25_days_outdated_when_all_supported_and_beta_allowed_other:
          type: number
          format: float
          description: p25 days outdated when all supported and beta are allowed for other devices
        os_p50_days_outdated_when_all_supported_and_beta_allowed_all:
          type: number
          format: float
          description: median days outdated when all supported and beta are allowed for all devices
        os_p50_days_outdated_when_all_supported_and_beta_allowed_windows:
          type: number
          format: float
          description: median days outdated when all supported and beta are allowed for Windows devices
        os_p50_days_outdated_when_all_supported_and_beta_allowed_macos:
          type: number
          format: float
          description: median days outdated when all supported and beta are allowed for macOS devices
        os_p50_days_outdated_when_all_supported_and_beta_allowed_linux:
          type: number
          format: float
          description: median days outdated when all supported and beta are allowed for Linux devices
        os_p50_days_outdated_when_all_supported_and_beta_allowed_ios:
          type: number
          format: float
          description: median days outdated when all supported and beta are allowed for iOS devices
        os_p50_days_outdated_when_all_supported_and_beta_allowed_ipados:
          type: number
          format: float
          description: median days outdated when all supported and beta are allowed for iPadOS devices
        os_p50_days_outdated_when_all_supported_and_beta_allowed_android:
          type: number
          format: float
          description: median days outdated when all supported and beta are allowed for Android devices
        os_p50_days_outdated_when_all_supported_and_beta_allowed_other:
          type: number
          format: float
          description: median days outdated when all supported and beta are allowed for Other devices
        os_p75_days_outdated_when_all_supported_and_beta_allowed_all:
          type: number
          format: float
          description: p75 days outdated when all supported and beta are allowed for all devices
        os_p75_days_outdated_when_all_supported_and_beta_allowed_windows:
          type: number
          format: float
          description: p75 days outdated when all supported and beta are allowed for Windows devices
        os_p75_days_outdated_when_all_supported_and_beta_allowed_macos:
          type: number
          format: float
          description: p75 days outdated when all supported and beta are allowed for macOS devices
        os_p75_days_outdated_when_all_supported_and_beta_allowed_linux:
          type: number
          format: float
          description: p75 days outdated when all supported and beta are allowed for Linux devices
        os_p75_days_outdated_when_all_supported_and_beta_allowed_ios:
          type: number
          format: float
          description: p75 days outdated when all supported and beta are allowed for iOS devices
        os_p75_days_outdated_when_all_supported_and_beta_allowed_ipados:
          type: number
          format: float
          description: p75 days outdated when all supported and beta are allowed for iPadOS devices
        os_p75_days_outdated_when_all_supported_and_beta_allowed_android:
          type: number
          format: float
          description: p75 days outdated when all supported and beta are allowed for Android devices
        os_p75_days_outdated_when_all_supported_and_beta_allowed_other:
          type: number
          format: float
          description: p75 days outdated when all supported and beta are allowed for Other devices
        os_p95_days_outdated_when_all_supported_and_beta_allowed_all:
          type: number
          format: float
          description: p95 days outdated when all supported and beta are allowed for all devices
        os_p95_days_outdated_when_all_supported_and_beta_allowed_windows:
          type: number
          format: float
          description: p95 days outdated when all supported and beta are allowed for Windows devices
        os_p95_days_outdated_when_all_supported_and_beta_allowed_macos:
          type: number
          format: float
          description: p95 days outdated when all supported and beta are allowed for macOS devices
        os_p95_days_outdated_when_all_supported_and_beta_allowed_linux:
          type: number
          format: float
          description: p95 days outdated when all supported and beta are allowed for Linux devices
        os_p95_days_outdated_when_all_supported_and_beta_allowed_ios:
          type: number
          format: float
          description: p95 days outdated when all supported and beta are allowed for iOS devices
        os_p95_days_outdated_when_all_supported_and_beta_allowed_ipados:
          type: number
          format: float
          description: p95 days outdated when all supported and beta are allowed for iPadOS devices
        os_p95_days_outdated_when_all_supported_and_beta_allowed_android:
          type: number
          format: float
          description: p95 days outdated when all supported and beta are allowed for Android devices
        os_p95_days_outdated_when_all_supported_and_beta_allowed_other:
          type: number
          format: float
          description: p95 days outdated when all supported and beta are allowed for Other devices
        os_p100_days_outdated_when_all_supported_and_beta_allowed_all:
          type: number
          format: float
          description: p100 days outdated when all supported and beta are allowed for all devices
        os_p100_days_outdated_when_all_supported_and_beta_allowed_windows:
          type: number
          format: float
          description: p100 days outdated when all supported and beta are allowed for Windows devices
        os_p100_days_outdated_when_all_supported_and_beta_allowed_macos:
          type: number
          format: float
          description: p100 days outdated when all supported and beta are allowed for macOS devices
        os_p100_days_outdated_when_all_supported_and_beta_allowed_linux:
          type: number
          format: float
          description: p100 days outdated when all supported and beta are allowed for Linux devices
        os_p100_days_outdated_when_all_supported_and_beta_allowed_ios:
          type: number
          format: float
          description: p100 days outdated when all supported and beta are allowed for iOS devices
        os_p100_days_outdated_when_all_supported_and_beta_allowed_ipados:
          type: number
          format: float
          description: p100 days outdated when all supported and beta are allowed for iPadOS devices
        os_p100_days_outdated_when_all_supported_and_beta_allowed_android:
          type: number
          format: float
          description: p100 days outdated when all supported and beta are allowed for Android devices
        os_p100_days_outdated_when_all_supported_and_beta_allowed_other:
          type: number
          format: float
          description: p100 days outdated when all supported and beta are allowed for Other devices
        os_avg_days_outdated_when_all_supported_and_beta_allowed_all:
          type: number
          format: float
          description: average days outdated when all supported and beta are allowed for all devices
        os_avg_days_outdated_when_all_supported_and_beta_allowed_windows:
          type: number
          format: float
          description: average days outdated when all supported and beta are allowed for Windows devices
        os_avg_days_outdated_when_all_supported_and_beta_allowed_macos:
          type: number
          format: float
          description: average days outdated when all supported and beta are allowed for macOS devices
        os_avg_days_outdated_when_all_supported_and_beta_allowed_linux:
          type: number
          format: float
          description: average days outdated when all supported and beta are allowed for Linux devices
        os_avg_days_outdated_when_all_supported_and_beta_allowed_ios:
          type: number
          format: float
          description: average days outdated when all supported and beta are allowed for iOS devices
        os_avg_days_outdated_when_all_supported_and_beta_allowed_ipados:
          type: number
          format: float
          description: average days outdated when all supported and beta are allowed for iPadOS devices
        os_avg_days_outdated_when_all_supported_and_beta_allowed_android:
          type: number
          format: float
          description: average days outdated when all supported and beta are allowed for Android devices
        os_avg_days_outdated_when_all_supported_and_beta_allowed_other:
          type: number
          format: float
          description: average days outdated when all supported and beta are allowed for Other devices
        disk_encryption_supported_all:
          type: integer
          description: Number of devices that have Disk Encryption supported (all operating systems)
        disk_encryption_supported_windows:
          type: integer
          description: Number of devices that have Disk Encryption supported and are Windows
        disk_encryption_supported_macos:
          type: integer
          description: Number of devices that have Disk Encryption supported and are macOS
        disk_encryption_supported_linux:
          type: integer
          description: Number of devices that have Disk Encryption supported and are Linux
        disk_encryption_supported_ios:
          type: integer
          description: Number of devices that have Disk Encryption supported and are iOS
        disk_encryption_supported_ipados:
          type: integer
          description: Number of devices that have Disk Encryption supported and are iPadOS
        disk_encryption_supported_android:
          type: integer
          description: Number of devices that have Disk Encryption supported and are Android
        disk_encryption_supported_other:
          type: integer
          description: Number of devices that have Disk Encryption supported and are other
        disk_encryption_active_all:
          type: integer
          description: Number of devices that have Disk Encryption active (all operating systems)
        disk_encryption_active_windows:
          type: integer
          description: Number of devices that have Disk Encryption active and are Windows
        disk_encryption_active_macos:
          type: integer
          description: Number of devices that have Disk Encryption active and are macOS
        disk_encryption_active_linux:
          type: integer
          description: Number of devices that have Disk Encryption active and are Linux
        disk_encryption_active_ios:
          type: integer
          description: Number of devices that have Disk Encryption active and are iOS
        disk_encryption_active_ipados:
          type: integer
          description: Number of devices that have Disk Encryption active and are iPadOS
        disk_encryption_active_android:
          type: integer
          description: Number of devices that have Disk Encryption active and are Android
        disk_encryption_active_other:
          type: integer
          description: Number of devices that have Disk Encryption active and are other
        disk_encryption_inactive_all:
          type: integer
          description: Number of devices that have Disk Encryption inactive (all operating systems)
        disk_encryption_inactive_windows:
          type: integer
          description: Number of devices that have Disk Encryption inactive and are Windows
        disk_encryption_inactive_macos:
          type: integer
          description: Number of devices that have Disk Encryption inactive and are macOS
        disk_encryption_inactive_linux:
          type: integer
          description: Number of devices that have Disk Encryption inactive and are Linux
        disk_encryption_inactive_ios:
          type: integer
          description: Number of devices that have Disk Encryption inactive and are iOS
        disk_encryption_inactive_ipados:
          type: integer
          description: Number of devices that have Disk Encryption inactive and are iPadOS
        disk_encryption_inactive_android:
          type: integer
          description: Number of devices that have Disk Encryption inactive and are Android
        disk_encryption_inactive_other:
          type: integer
          description: Number of devices that have Disk Encryption inactive and are other
        disk_encryption_known_all:
          type: integer
          description: Number of devices that have the OS check known (all operating systems)
        disk_encryption_known_windows:
          type: integer
          description: Number of devices that have the OS check known and are Windows
        disk_encryption_known_macos:
          type: integer
          description: Number of devices that have the OS check known and are macOS
        disk_encryption_known_linux:
          type: integer
          description: Number of devices that have the OS check known and are Linux
        disk_encryption_known_ios:
          type: integer
          description: Number of devices that have the OS check known and are iOS
        disk_encryption_known_ipados:
          type: integer
          description: Number of devices that have the OS check known and are iPadOS
        disk_encryption_known_android:
          type: integer
          description: Number of devices that have the OS check known and are Android
        disk_encryption_known_other:
          type: integer
          description: Number of devices that have the OS check known and are other
        screen_lock_active_all:
          type: integer
          description: Number of devices that have Screen Lock active (all operating systems)
        screen_lock_active_windows:
          type: integer
          description: Number of devices that have Screen Lock active and are Windows
        screen_lock_active_macos:
          type: integer
          description: Number of devices that have Screen Lock active and are macOS
        screen_lock_active_linux:
          type: integer
          description: Number of devices that have Screen Lock active and are Linux
        screen_lock_active_ios:
          type: integer
          description: Number of devices that have Screen Lock active and are iOS
        screen_lock_active_ipados:
          type: integer
          description: Number of devices that have Screen Lock active and are iPadOS
        screen_lock_active_android:
          type: integer
          description: Number of devices that have Screen Lock active and are Android
        screen_lock_active_other:
          type: integer
          description: Number of devices that have Screen Lock active and are other
        screen_lock_inactive_all:
          type: integer
          description: Number of devices that have Screen Lock inactive (all operating systems)
        screen_lock_inactive_windows:
          type: integer
          description: Number of devices that have Screen Lock inactive and are Windows
        screen_lock_inactive_macos:
          type: integer
          description: Number of devices that have Screen Lock inactive and are macOS
        screen_lock_inactive_linux:
          type: integer
          description: Number of devices that have Screen Lock inactive and are Linux
        screen_lock_inactive_ios:
          type: integer
          description: Number of devices that have Screen Lock inactive and are iOS
        screen_lock_inactive_ipados:
          type: integer
          description: Number of devices that have Screen Lock inactive and are iPadOS
        screen_lock_inactive_android:
          type: integer
          description: Number of devices that have Screen Lock inactive and are Android
        screen_lock_inactive_other:
          type: integer
          description: Number of devices that have Screen Lock inactive and are other
        screen_lock_known_all:
          type: integer
          description: Number of devices that have Screen Lock check known (all operating systems)
        screen_lock_known_windows:
          type: integer
          description: Number of devices that have Screen Lock check known and are Windows
        screen_lock_known_macos:
          type: integer
          description: Number of devices that have Screen Lock check known and are macOS
        screen_lock_known_linux:
          type: integer
          description: Number of devices that have Screen Lock check known and are Linux
        screen_lock_known_ios:
          type: integer
          description: Number of devices that have Screen Lock check known and are iOS
        screen_lock_known_ipados:
          type: integer
          description: Number of devices that have Screen Lock check known and are iPadOS
        screen_lock_known_android:
          type: integer
          description: Number of devices that have Screen Lock check known and are Android
        screen_lock_known_other:
          type: integer
          description: Number of devices that have Screen Lock check known and are other
        browser_check_supported_all:
          type: integer
          description: Number of devices that support the browser check (all operating systems)
        browser_known_all:
          type: integer
          description: Number of devices that have browser version information known (all operating systems)
        browser_time_outdated_in_days_all:
          type: array
          items:
            type: number
            format: float
          description: Array of total days outdated across all browsers for all devices
        browser_total_up_to_date_all:
          type: integer
          description: Number of devices that have all browsers up to date for all devices
        browser_total_outdated_all:
          type: integer
          description: Number of devices that have any browsers outdated for all devices
        browser_p0_days_outdated_all:
          type: number
          format: float
          description: P0 total days outdated across all browsers for all devices
        browser_p5_days_outdated_all:
          type: number
          format: float
          description: P5 total days outdated across all browsers for all devices
        browser_p25_days_outdated_all:
          type: number
          format: float
          description: P25 total days outdated across all browsers for all devices
        browser_p50_days_outdated_all:
          type: number
          format: float
          description: P50 (median) total days outdated across all browsers for all devices
        browser_p75_days_outdated_all:
          type: number
          format: float
          description: P75 total days outdated across all browsers for all devices
        browser_p95_days_outdated_all:
          type: number
          format: float
          description: P95 total days outdated across all browsers for all devices
        browser_p100_days_outdated_all:
          type: number
          format: float
          description: P100 total days outdated across all browsers for all devices
        browser_avg_days_outdated_all:
          type: number
          format: float
          description: Average total days outdated across all browsers for all devices
        secure_boot_supported_all:
          type: integer
          description: Number of devices that have Secure Boot supported (all operating systems)
        secure_boot_supported_windows:
          type: integer
          description: Number of devices that have Secure Boot supported and are Windows
        secure_boot_supported_macos:
          type: integer
          description: Number of devices that have Secure Boot supported and are macOS
        secure_boot_supported_linux:
          type: integer
          description: Number of devices that have Secure Boot supported and are Linux
        secure_boot_supported_ios:
          type: integer
          description: Number of devices that have Secure Boot supported and are iOS
        secure_boot_supported_ipados:
          type: integer
          description: Number of devices that have Secure Boot supported and are iPadOS
        secure_boot_supported_android:
          type: integer
          description: Number of devices that have Secure Boot supported and are Android
        secure_boot_supported_other:
          type: integer
          description: Number of devices that have Secure Boot supported and are other
        secure_boot_active_all:
          type: integer
          description: Number of devices that have Secure Boot active (all operating systems)
        secure_boot_active_windows:
          type: integer
          description: Number of devices that have Secure Boot active and are Windows
        secure_boot_active_macos:
          type: integer
          description: Number of devices that have Secure Boot active and are macOS
        secure_boot_active_linux:
          type: integer
          description: Number of devices that have Secure Boot active and are Linux
        secure_boot_active_ios:
          type: integer
          description: Number of devices that have Secure Boot active and are iOS
        secure_boot_active_ipados:
          type: integer
          description: Number of devices that have Secure Boot active and are iPadOS
        secure_boot_active_android:
          type: integer
          description: Number of devices that have Secure Boot active and are Android
        secure_boot_active_other:
          type: integer
          description: Number of devices that have Secure Boot active and are other
        secure_boot_inactive_all:
          type: integer
          description: Number of devices that have Secure Boot inactive (all operating systems)
        secure_boot_inactive_windows:
          type: integer
          description: Number of devices that have Secure Boot inactive and are Windows
        secure_boot_inactive_macos:
          type: integer
          description: Number of devices that have Secure Boot inactive and are macOS
        secure_boot_inactive_linux:
          type: integer
          description: Number of devices that have Secure Boot inactive and are Linux
        secure_boot_inactive_ios:
          type: integer
          description: Number of devices that have Secure Boot inactive and are iOS
        secure_boot_inactive_ipados:
          type: integer
          description: Number of devices that have Secure Boot inactive and are iPadOS
        secure_boot_inactive_android:
          type: integer
          description: Number of devices that have Secure Boot inactive and are Android
        secure_boot_inactive_other:
          type: integer
          description: Number of devices that have Secure Boot inactive and are other
        secure_boot_known_all:
          type: integer
          description: Number of devices that have Secure Boot check known (all operating systems)
        secure_boot_known_windows:
          type: integer
          description: Number of devices that have Secure Boot check known and are Windows
        secure_boot_known_macos:
          type: integer
          description: Number of devices that have Secure Boot check known and are macOS
        secure_boot_known_linux:
          type: integer
          description: Number of devices that have Secure Boot check known and are Linux
        secure_boot_known_ios:
          type: integer
          description: Number of devices that have Secure Boot check known and are iOS
        secure_boot_known_ipados:
          type: integer
          description: Number of devices that have Secure Boot check known and are iPadOS
        secure_boot_known_android:
          type: integer
          description: Number of devices that have Secure Boot check known and are Android
        secure_boot_known_other:
          type: integer
          description: Number of devices that have Secure Boot check known and are other
        secure_boot_status_ok_all:
          type: integer
          description: Number of devices with Secure Boot status OK (all operating systems)
        secure_boot_status_ok_windows:
          type: integer
          description: Number of devices with Secure Boot status OK and are Windows
        secure_boot_status_ok_macos:
          type: integer
          description: Number of devices with Secure Boot status OK and are macOS
        secure_boot_status_ok_linux:
          type: integer
          description: Number of devices with Secure Boot status OK and are Linux
        secure_boot_status_ok_ios:
          type: integer
          description: Number of devices with Secure Boot status OK and are iOS
        secure_boot_status_ok_ipados:
          type: integer
          description: Number of devices with Secure Boot status OK and are iPadOS
        secure_boot_status_ok_android:
          type: integer
          description: Number of devices with Secure Boot status OK and are Android
        secure_boot_status_ok_other:
          type: integer
          description: Number of devices with Secure Boot status OK and are other
        secure_boot_status_warning_all:
          type: integer
          description: Number of devices with Secure Boot status WARNING (all operating systems)
        secure_boot_status_warning_windows:
          type: integer
          description: Number of devices with Secure Boot status WARNING and are Windows
        secure_boot_status_warning_macos:
          type: integer
          description: Number of devices with Secure Boot status WARNING and are macOS
        secure_boot_status_warning_linux:
          type: integer
          description: Number of devices with Secure Boot status WARNING and are Linux
        secure_boot_status_warning_ios:
          type: integer
          description: Number of devices with Secure Boot status WARNING and are iOS
        secure_boot_status_warning_ipados:
          type: integer
          description: Number of devices with Secure Boot status WARNING and are iPadOS
        secure_boot_status_warning_android:
          type: integer
          description: Number of devices with Secure Boot status WARNING and are Android
        secure_boot_status_warning_other:
          type: integer
          description: Number of devices with Secure Boot status WARNING and are other
        secure_boot_status_blocking_all:
          type: integer
          description: Number of devices with Secure Boot status BLOCKING (all operating systems)
        secure_boot_status_blocking_windows:
          type: integer
          description: Number of devices with Secure Boot status BLOCKING and are Windows
        secure_boot_status_blocking_macos:
          type: integer
          description: Number of devices with Secure Boot status BLOCKING and are macOS
        secure_boot_status_blocking_linux:
          type: integer
          description: Number of devices with Secure Boot status BLOCKING and are Linux
        secure_boot_status_blocking_ios:
          type: integer
          description: Number of devices with Secure Boot status BLOCKING and are iOS
        secure_boot_status_blocking_ipados:
          type: integer
          description: Number of devices with Secure Boot status BLOCKING and are iPadOS
        secure_boot_status_blocking_android:
          type: integer
          description: Number of devices with Secure Boot status BLOCKING and are Android
        secure_boot_status_blocking_other:
          type: integer
          description: Number of devices with Secure Boot status BLOCKING and are other
        secure_boot_status_missing_all:
          type: integer
          description: Number of devices with Secure Boot status MISSING (all operating systems)
        secure_boot_status_missing_windows:
          type: integer
          description: Number of devices with Secure Boot status MISSING and are Windows
        secure_boot_status_missing_macos:
          type: integer
          description: Number of devices with Secure Boot status MISSING and are macOS
        secure_boot_status_missing_linux:
          type: integer
          description: Number of devices with Secure Boot status MISSING and are Linux
        secure_boot_status_missing_ios:
          type: integer
          description: Number of devices with Secure Boot status MISSING and are iOS
        secure_boot_status_missing_ipados:
          type: integer
          description: Number of devices with Secure Boot status MISSING and are iPadOS
        secure_boot_status_missing_android:
          type: integer
          description: Number of devices with Secure Boot status MISSING and are Android
        secure_boot_status_missing_other:
          type: integer
          description: Number of devices with Secure Boot status MISSING and are other
        integrity_protection_supported_all:
          type: integer
          description: Number of devices that have Integrity Protection supported (all operating systems)
        integrity_protection_supported_windows:
          type: integer
          description: Number of devices that have Integrity Protection supported and are Windows
        integrity_protection_supported_macos:
          type: integer
          description: Number of devices that have Integrity Protection supported and are macOS
        integrity_protection_supported_linux:
          type: integer
          description: Number of devices that have Integrity Protection supported and are Linux
        integrity_protection_supported_ios:
          type: integer
          description: Number of devices that have Integrity Protection supported and are iOS
        integrity_protection_supported_ipados:
          type: integer
          description: Number of devices that have Integrity Protection supported and are iPadOS
        integrity_protection_supported_android:
          type: integer
          description: Number of devices that have Integrity Protection supported and are Android
        integrity_protection_supported_other:
          type: integer
          description: Number of devices that have Integrity Protection supported and are other
        integrity_protection_active_all:
          type: integer
          description: Number of devices that have Integrity Protection active (all operating systems)
        integrity_protection_active_windows:
          type: integer
          description: Number of devices that have Integrity Protection active and are Windows
        integrity_protection_active_macos:
          type: integer
          description: Number of devices that have Integrity Protection active and are macOS
        integrity_protection_active_linux:
          type: integer
          description: Number of devices that have Integrity Protection active and are Linux
        integrity_protection_active_ios:
          type: integer
          description: Number of devices that have Integrity Protection active and are iOS
        integrity_protection_active_ipados:
          type: integer
          description: Number of devices that have Integrity Protection active and are iPadOS
        integrity_protection_active_android:
          type: integer
          description: Number of devices that have Integrity Protection active and are Android
        integrity_protection_active_other:
          type: integer
          description: Number of devices that have Integrity Protection active and are other
        integrity_protection_inactive_all:
          type: integer
          description: Number of devices that have Integrity Protection inactive (all operating systems)
        integrity_protection_inactive_windows:
          type: integer
          description: Number of devices that have Integrity Protection inactive and are Windows
        integrity_protection_inactive_macos:
          type: integer
          description: Number of devices that have Integrity Protection inactive and are macOS
        integrity_protection_inactive_linux:
          type: integer
          description: Number of devices that have Integrity Protection inactive and are Linux
        integrity_protection_inactive_ios:
          type: integer
          description: Number of devices that have Integrity Protection inactive and are iOS
        integrity_protection_inactive_ipados:
          type: integer
          description: Number of devices that have Integrity Protection inactive and are iPadOS
        integrity_protection_inactive_android:
          type: integer
          description: Number of devices that have Integrity Protection inactive and are Android
        integrity_protection_inactive_other:
          type: integer
          description: Number of devices that have Integrity Protection inactive and are other
        integrity_protection_known_all:
          type: integer
          description: Number of devices that have Integrity Protection check known (all operating systems)
        integrity_protection_known_windows:
          type: integer
          description: Number of devices that have Integrity Protection check known and are Windows
        integrity_protection_known_macos:
          type: integer
          description: Number of devices that have Integrity Protection check known and are macOS
        integrity_protection_known_linux:
          type: integer
          description: Number of devices that have Integrity Protection check known and are Linux
        integrity_protection_known_ios:
          type: integer
          description: Number of devices that have Integrity Protection check known and are iOS
        integrity_protection_known_ipados:
          type: integer
          description: Number of devices that have Integrity Protection check known and are iPadOS
        integrity_protection_known_android:
          type: integer
          description: Number of devices that have Integrity Protection check known and are Android
        integrity_protection_known_other:
          type: integer
          description: Number of devices that have Integrity Protection check known and are other
        integrity_protection_status_supported_all:
          type: integer
          description: Number of devices with Integrity Protection status supported (all operating systems)
        integrity_protection_status_supported_windows:
          type: integer
          description: Number of devices with Integrity Protection status supported and are Windows
        integrity_protection_status_supported_macos:
          type: integer
          description: Number of devices with Integrity Protection status supported and are macOS
        integrity_protection_status_supported_linux:
          type: integer
          description: Number of devices with Integrity Protection status supported and are Linux
        integrity_protection_status_supported_ios:
          type: integer
          description: Number of devices with Integrity Protection status supported and are iOS
        integrity_protection_status_supported_ipados:
          type: integer
          description: Number of devices with Integrity Protection status supported and are iPadOS
        integrity_protection_status_supported_android:
          type: integer
          description: Number of devices with Integrity Protection status supported and are Android
        integrity_protection_status_supported_other:
          type: integer
          description: Number of devices with Integrity Protection status supported and are other
        integrity_protection_status_active_all:
          type: integer
          description: Number of devices with Integrity Protection status active (all operating systems)
        integrity_protection_status_active_windows:
          type: integer
          description: Number of devices with Integrity Protection status active and are Windows
        integrity_protection_status_active_macos:
          type: integer
          description: Number of devices with Integrity Protection status active and are macOS
        integrity_protection_status_active_linux:
          type: integer
          description: Number of devices with Integrity Protection status active and are Linux
        integrity_protection_status_active_ios:
          type: integer
          description: Number of devices with Integrity Protection status active and are iOS
        integrity_protection_status_active_ipados:
          type: integer
          description: Number of devices with Integrity Protection status active and are iPadOS
        integrity_protection_status_active_android:
          type: integer
          description: Number of devices with Integrity Protection status active and are Android
        integrity_protection_status_active_other:
          type: integer
          description: Number of devices with Integrity Protection status active and are other
        integrity_protection_status_inactive_all:
          type: integer
          description: Number of devices with Integrity Protection status inactive (all operating systems)
        integrity_protection_status_inactive_windows:
          type: integer
          description: Number of devices with Integrity Protection status inactive and are Windows
        integrity_protection_status_inactive_macos:
          type: integer
          description: Number of devices with Integrity Protection status inactive and are macOS
        integrity_protection_status_inactive_linux:
          type: integer
          description: Number of devices with Integrity Protection status inactive and are Linux
        integrity_protection_status_inactive_ios:
          type: integer
          description: Number of devices with Integrity Protection status inactive and are iOS
        integrity_protection_status_inactive_ipados:
          type: integer
          description: Number of devices with Integrity Protection status inactive and are iPadOS
        integrity_protection_status_inactive_android:
          type: integer
          description: Number of devices with Integrity Protection status inactive and are Android
        integrity_protection_status_inactive_other:
          type: integer
          description: Number of devices with Integrity Protection status inactive and are other
        integrity_protection_status_unknown_all:
          type: integer
          description: Number of devices with Integrity Protection status unknown (all operating systems)
        integrity_protection_status_unknown_windows:
          type: integer
          description: Number of devices with Integrity Protection status unknown and are Windows
        integrity_protection_status_unknown_macos:
          type: integer
          description: Number of devices with Integrity Protection status unknown and are macOS
        integrity_protection_status_unknown_linux:
          type: integer
          description: Number of devices with Integrity Protection status unknown and are Linux
        integrity_protection_status_unknown_ios:
          type: integer
          description: Number of devices with Integrity Protection status unknown and are iOS
        integrity_protection_status_unknown_ipados:
          type: integer
          description: Number of devices with Integrity Protection status unknown and are iPadOS
        integrity_protection_status_unknown_android:
          type: integer
          description: Number of devices with Integrity Protection status unknown and are Android
        integrity_protection_status_unknown_other:
          type: integer
          description: Number of devices with Integrity Protection status unknown and are other
      required:
        - organization_id
        - target_date_unix
        - target_date_end_unix
        - number_devices_total
    SingleDiscoveryResponse:
      type: object
      properties:
        application_id:
          type: string
          description: ID of the application
    SingleDiscoveryRequest:
      type: object
      description: 'Request for a single (accountless) discovery scan. Two variants: the delegated (auth-code) variant supplies `code` + `redirect_uri`; the Microsoft app-only (admin-consent) variant supplies `tenant_id` instead (no OAuth code) and requires `email` as the report recipient. Only `type` is required for every request; the remaining fields are validated conditionally based on which variant is used.'
      properties:
        code:
          type: string
          description: Authorization code (delegated variant)
        redirect_uri:
          type: string
          description: Redirect URI for the auth service (delegated variant)
        tenant_id:
          type: string
          format: uuid
          description: 'Microsoft Entra tenant id. When set, selects the app-only (admin-consent) variant, which persists an app-only connection and does not exchange an OAuth code. Microsoft only.'
        type:
          type: string
          description: type of auth service
          enum:
            - Google
            - Microsoft
        email:
          type: string
          description: 'Report recipient email. Optional for the delegated variant (derived from the connecting user when omitted); required for the app-only variant, which has no connecting user.'
      required:
        - type
    Transactions:
      type: object
      properties:
        application:
          $ref: '#/components/schemas/Application'
        decisions:
          $ref: '#/components/schemas/Decisions'
    Type:
      type: string
      description: Type of the application
      enum:
        - MicrosoftEAM
        - Okta
        - Onelogin
        - Google
        - Microsoft
        - OktaDiscovery
        - IdP
    User:
      type: object
      properties:
        username:
          type: string
          description: Username of the user
        full_name:
          type: string
          description: Full name of the user
      required:
        - username
        - full_name
    UserDetails:
      type: object
      properties:
        firstName:
          type: string
        lastName:
          type: string
        language:
          type: string
        groups:
          type: array
          items:
            type: string
    SecurityStatus:
      type: string
      enum:
        - OK
        - WARNING
        - BLOCKING
        - MISSING
      description: Security status indicating compliance level
