GraphQL

Introspection

A GraphQL schema can describe itself. Introspection is the built-in facility by which a client queries the schema about the schema — every type, field, argument, doc string, and deprecation — using ordinary GraphQL queries. It is the reason GraphQL tooling feels magical, and it is also something you must make a deliberate production decision about.

The Meta Fields

Three meta fields power introspection, all implicitly available without appearing in your SDL:

  • __typename — on any object: the concrete type's name as a string. Used constantly with unions and interfaces.
  • __schema — on the root query type: the full schema description.
  • __type(name: "...") — on the root query type: one named type's description.

Asking a server what types it has:

{
  __schema {
    queryType { name }
    types {
      name
      kind
    }
  }
}

The response lists every type — your Artist and Album, the built-in scalars, and the introspection types themselves (they all start with __). The kind field reports the type's category: OBJECT, SCALAR, ENUM, INTERFACE, UNION, INPUT_OBJECT, LIST, NON_NULL.

Drilling into one type:

{
  __type(name: "Album") {
    name
    description
    fields {
      name
      description
      isDeprecated
      deprecationReason
      type {
        kind
        name
        ofType { kind name }
      }
    }
  }
}

Note the nested ofType: wrapper types are represented as a chain, so [Track!]! comes back as NON_NULLLISTNON_NULLTrack. Walking ofType until you hit a named type is how tools print readable type signatures.

What Introspection Powers

Nearly the entire GraphQL developer experience is introspection-driven:

  • IDEs and playgrounds (GraphiQL and friends) fetch the schema once, then offer autocompletion, inline docs, and instant validation as you type.
  • Documentation is generated straight from the schema — the doc strings you wrote in SDL are the docs.
  • Code generation: client tools introspect the schema and emit typed models and query builders, keeping frontend types mechanically in sync with the API.
  • Schema diffing and linting in CI: dump the schema on each build and compare against the previous version to catch breaking changes before deploy. A schema dump belongs in your build artifacts the same way a lockfile does.
  • Deprecation tracking: isDeprecated and deprecationReason are ordinary introspectable data, which is how tools warn about deprecated field usage.

The Production Decision

Introspection tells anyone who can reach the endpoint your entire API surface — including fields you added for one internal client, admin mutations, and half-finished experiments. For a public API that is fine and even desirable: the schema is the documentation. For an internal or partner API, most teams disable introspection in production (implementations expose this as a validation-rule toggle; in graphql-php you disable the introspection validation rule) while keeping it on in development environments.

Two honest caveats. First, disabling introspection is not access control — the fields still exist and still execute for anyone who guesses or reverse-engineers them from your client bundle. Real protection is the authorization work in a later lesson; hiding the map does not lock the doors. Second, your own tooling (codegen, CI diffing) needs the schema from somewhere, so pair the production toggle with a build-time schema artifact rather than pointing tools at production.

A middle path used by some teams: leave introspection on but strip sensitive types from a separate public schema, or require an authenticated/internal role for introspection queries. Whatever you choose, choose it on purpose rather than shipping the default without thinking.

Reading Other People's APIs

Introspection is also a consumer skill. Pointed at any GraphQL endpoint that allows it, a single introspection query hands you the complete, accurate contract — no stale docs. When you integrate with a third-party GraphQL API, start by loading its schema into a client IDE and exploring; when their docs and their schema disagree, the schema is the one that is true.

What To Check

Before moving on, make sure you can:

  • name the three meta fields and what each returns
  • query __type for a type's fields, including unwrapping ofType chains
  • list several tools and workflows that depend on introspection
  • explain why disabling introspection is not a security boundary, and what actually is
  • describe how CI can use schema dumps to catch breaking changes

What You Should Be Able To Do

After this lesson, you should be able to explore an unfamiliar GraphQL API using introspection queries alone, wire your own project's tooling (docs, codegen, schema diffing) to schema dumps, and make — and defend — a deliberate decision about introspection exposure in each of your environments.