> ## Documentation Index
> Fetch the complete documentation index at: https://developers.mypilotindex.com/llms.txt
> Use this file to discover all available pages before exploring further.

# List the partner's grants

> The partner's grants, live and revoked, in the order they last changed (granted, or revoked), then by id, for reconciling after a missed webhook: page with next_cursor until it is null. status keeps the live or the revoked ones; changed_since keeps those granted or revoked at or after it. A grant whose pilot deleted his account is removed with the account and appears in no list; its grant.revoked event was queued first.



## OpenAPI

````yaml /api-reference/partner.yaml get /v1/partner/grants
openapi: 3.1.0
info:
  title: MyPilotIndex Partner API
  version: 1.0.0
  description: >-
    The API of approved partner applications, such as logbooks, that act for a
    pilot who has granted them access on the MyPilotIndex consent screen. It is
    a separate document from the member API (openapi.yaml): partner routes live
    under /v1/partner/ and are never served to browsers. Authenticate with an
    access token from the identity provider's token endpoint
    (grant_type=client_credentials, scopes partner/<scope>) in the Authorization
    header. Every authenticated answer carries X-RateLimit-Limit and
    X-RateLimit-Remaining, the partner's daily allowance and what is left of it
    (a 401, and a path or method outside this document, carry neither); past the
    allowance the API answers 429 rate_limited with Retry-After. Errors use the
    shared envelope below. The API is additive within v1: new fields and routes
    may appear, existing ones do not change meaning.
servers:
  - url: https://{devApiHost}
    description: >-
      Sandbox on the AWS dev environment, with synthetic pilots. The host is
      issued to the partner with its sandbox credential.
    variables:
      devApiHost:
        default: dev-api.mypilotindex.com
        description: The dev API host given to the partner with the sandbox credential.
security: []
tags:
  - name: Grants
    description: >-
      A pilot connects on MyPilotIndex: the partner sends his browser to the
      consent page
      (https://mypilotindex.com/connect/{slug}?client_id&redirect_uri&scope&state&code_challenge&code_challenge_method=S256),
      the pilot signs in and allows, and the browser returns to the registered
      redirect_uri with code and state (or error=access_denied and state when he
      denies). The partner exchanges the code here for a grant and the pilot's
      pairwise id, which signs the pilot in ("Sign in with MyPilotIndex") and
      names him on every later call. A grant that is revoked, unknown or another
      partner's answers 404 on every route, identically.
  - name: Certificates
    description: >-
      Check a certificate a pilot shows you, such as his MPI Report, by its
      public id. The answer is the public verification's, and the call needs no
      grant.
  - name: Webhooks
    description: >-
      MyPilotIndex tells a partner about its grants by webhook: grant.revoked
      when a grant ends, and ping when the partner asks for a test. The webhook
      URL (https only) and its signing secret are set by MyPilotIndex when the
      partner is approved; the secret is shown once. Each event is a POST of the
      event as JSON (Content-Type application/json) signed in the Standard
      Webhooks scheme: webhook-id (the event id), webhook-timestamp and
      webhook-signature, "v1," and the base64 HMAC-SHA256 of
      "<webhook-id>.<webhook-timestamp>.<body>" under the key the secret carries
      in base64 after its whsec_ prefix, over the exact bytes received. Verify
      the signature, refuse a timestamp more than five minutes from your clock,
      dedupe on webhook-id, and answer any 2xx within 10 seconds. A 5xx, a 408,
      a 429, a redirect (never followed), a timeout or a connection failure is
      retried with growing gaps for about a day (twelve attempts), with the same
      webhook-id and a fresh timestamp and signature. A 4xx other than 408 and
      429 is taken as a refusal and not retried, except for a grant.revoked
      event with reason account_deleted: its grant leaves every list with the
      account, so it cannot be reconciled later, and it is retried within the
      same window on any answer but a 2xx, a 4xx included. A partner that missed
      other events reconciles with GET
      /v1/partner/grants?status=revoked&changed_since=.
paths:
  /v1/partner/grants:
    get:
      tags:
        - Grants
      summary: List the partner's grants
      description: >-
        The partner's grants, live and revoked, in the order they last changed
        (granted, or revoked), then by id, for reconciling after a missed
        webhook: page with next_cursor until it is null. status keeps the live
        or the revoked ones; changed_since keeps those granted or revoked at or
        after it. A grant whose pilot deleted his account is removed with the
        account and appears in no list; its grant.revoked event was queued
        first.
      operationId: partners.list_grants.v1
      parameters:
        - name: status
          in: query
          required: false
          description: active (live) or revoked; absent lists both.
          schema:
            type: string
            enum:
              - active
              - revoked
        - name: changed_since
          in: query
          required: false
          description: >-
            An RFC 3339 timestamp; only grants granted or revoked at or after
            it.
          schema:
            type: string
            format: date-time
        - name: limit
          in: query
          required: false
          schema:
            type: integer
            minimum: 1
            maximum: 500
            default: 100
        - name: cursor
          in: query
          required: false
          description: The next_cursor of the previous page, as it came; opaque.
          schema:
            type: string
      responses:
        '200':
          description: One page of grants.
          headers:
            X-RateLimit-Limit:
              $ref: '#/components/headers/RateLimitLimit'
            X-RateLimit-Remaining:
              $ref: '#/components/headers/RateLimitRemaining'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/GrantPage'
              example:
                items:
                  - grant_id: 6f1c2a9e-3b7d-4c51-9e2a-0d4b8f6a1c33
                    pilot_id: 2d9b7c1e-8f4a-4e3b-a6d5-91c0f2e7b844
                    scopes:
                      - hours.write
                      - profile
                    granted_at: '2026-11-04T12:00:00Z'
                    revoked_at: '2026-11-05T09:30:00Z'
                    revoked_reason: pilot
                next_cursor: null
        '400':
          $ref: '#/components/responses/Error'
        '401':
          $ref: '#/components/responses/Error'
        '405':
          $ref: '#/components/responses/Error'
        '429':
          $ref: '#/components/responses/RateLimited'
        '500':
          $ref: '#/components/responses/Error'
        '503':
          $ref: '#/components/responses/Error'
        '504':
          $ref: '#/components/responses/Error'
      security:
        - partnerOAuth: []
components:
  headers:
    RateLimitLimit:
      description: >-
        The partner's daily allowance of calls (1,000 unless agreed otherwise),
        per UTC day.
      schema:
        type: integer
    RateLimitRemaining:
      description: What is left of the allowance after this call.
      schema:
        type: integer
    RetryAfter:
      description: >-
        The HTTP date, in UTC, when the allowance renews (the next UTC
        midnight).
      schema:
        type: string
        example: Thu, 05 Nov 2026 00:00:00 GMT
  schemas:
    GrantPage:
      type: object
      additionalProperties: false
      required:
        - items
        - next_cursor
      properties:
        items:
          type: array
          items:
            $ref: '#/components/schemas/ListedGrant'
        next_cursor:
          type:
            - string
            - 'null'
          description: Continues the list after the last item; null on the last page.
    ListedGrant:
      type: object
      additionalProperties: false
      required:
        - grant_id
        - pilot_id
        - scopes
        - granted_at
        - revoked_at
        - revoked_reason
      properties:
        grant_id:
          type: string
          format: uuid
        pilot_id:
          type: string
          format: uuid
        scopes:
          type: array
          items:
            $ref: '#/components/schemas/Scope'
        granted_at:
          type: string
          format: date-time
        revoked_at:
          type:
            - string
            - 'null'
          format: date-time
        revoked_reason:
          type:
            - string
            - 'null'
          enum:
            - pilot
            - operator
            - account_deleted
            - null
          description: Who revoked the grant; null while it is live.
    Error:
      type: object
      additionalProperties: false
      required:
        - error
      properties:
        error:
          type: object
          additionalProperties: false
          required:
            - code
            - message
            - correlation_id
          properties:
            code:
              type: string
              enum:
                - invalid_request
                - request_too_large
                - unauthenticated
                - not_found
                - conflict
                - unprocessable
                - operation_disabled
                - rate_limited
                - forbidden
                - dependency_unavailable
                - internal
                - deadline_exceeded
                - method_not_allowed
            message:
              type: string
              description: Stable safe English message, never the underlying error text.
            correlation_id:
              type: string
              pattern: ^[a-f0-9]{32}$
            reason:
              type: string
              description: Optional refusal reason from the operation's closed vocabulary.
    RateLimitedError:
      allOf:
        - $ref: '#/components/schemas/Error'
        - type: object
          properties:
            error:
              type: object
              properties:
                reason:
                  type: string
                  enum:
                    - rate_limited
    Scope:
      type: string
      enum:
        - profile
        - score
        - hours.read
        - hours.write
        - licenses
        - applications
      description: >-
        A scope the pilot granted, without the partner/ prefix of the token's
        scopes.
  responses:
    Error:
      description: The shared error envelope.
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
    RateLimited:
      description: >-
        rate_limited with reason rate_limited, past the partner's daily
        allowance; nothing was done.
      headers:
        Retry-After:
          $ref: '#/components/headers/RetryAfter'
        X-RateLimit-Limit:
          $ref: '#/components/headers/RateLimitLimit'
        X-RateLimit-Remaining:
          $ref: '#/components/headers/RateLimitRemaining'
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/RateLimitedError'
  securitySchemes:
    partnerOAuth:
      type: oauth2
      description: >-
        OAuth 2.0 client credentials. Request a token from the token endpoint of
        the identity provider's domain (https://{cognito-domain}/oauth2/token,
        with HTTP Basic client authentication) and send it as a Bearer token.
        Production uses auth.mypilotindex.com. The sandbox uses the dev
        environment's Cognito domain, which is given to the partner with its
        sandbox credential. A token carries only the scopes the partner was
        approved for.
      flows:
        clientCredentials:
          tokenUrl: https://auth.mypilotindex.com/oauth2/token
          scopes:
            partner/profile: Read the pilot's name, photo and username.
            partner/score: Read the pilot's MPI Score and phase.
            partner/hours.read: Read the pilot's flight hours.
            partner/hours.write: Update the pilot's flight hours with the logbook's totals.
            partner/licenses: Read the pilot's licenses, ratings and type ratings.
            partner/applications: Read the pilot's applications to jobs from the partner's company.

````

This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.