Contributor-facing documentation for the Graphitron generator: how the pipeline classifies a GraphQL schema, what code it emits, and the design principles that govern both. For end-user documentation (writing schemas, wiring up Maven, running the generator), see the user manual.

You came here because…

You want to extend the runtime, wire per-request values into Graphitron.newExecutionInput(…​), register custom scalars, hook in jOOQ listeners. → Runtime Extension Points.

You’re integrating with Apollo Federation, the @link opt-in, the <schemaInput tag> flag, providing a custom entity fetcher. → Getting started → Federation.

You want to understand rejections, what AUTHOR_ERROR / INVALID_SCHEMA / DEFERRED actually mean in the builder, why rejection is a typed variant rather than a string, how Levenshtein candidate hints get attached. → Typed rejection.

You’re integrating an editor or agent with the dev loop, what the dev Mojo wires up, what the LSP / schema watcher / classpath watcher each watch, why idempotent writes matter. → Getting started → Dev loop.

You want to read the classification taxonomy, every variant the schema builder produces, every generator’s input. → Code Generation Triggers.

You’re looking for a deeper reference, the architectural principles that govern both classifier and emitter, the test-tier rubric, the unified argument-resolution lift, the dispatch-axis model behind DataLoader-backed source-side fields. → see Rewrite Design Principles, Test-tier guide, Argument Resolution, Dispatch axes. The ongoing-work view lives at Rewrite Roadmap.

Pipeline at a glance

flowchart LR
    A[".graphqls files"] --> B["RewriteSchemaLoader<br/>(parse + auto-inject<br/>directives.graphqls)"]
    B --> C["GraphitronSchemaBuilder<br/>(classify into<br/>GraphitronSchema)"]
    C --> D["GraphitronSchemaValidator<br/>(reject Unclassified*,<br/>surface diagnostics)"]
    D --> E["Generators<br/>(TypeFetcher / TypeClass /<br/>TypeConditions /<br/>QueryConditions / ...)"]
    E --> F["JavaFile.writeToPath<br/>(idempotent writes,<br/>orphan sweep)"]
    F --> G["consumer compile<br/>(graphitron-sakila-example<br/>verifies type + behaviour)"]

Three things to know about this pipeline that the diagram doesn’t show:

  1. The loader auto-injects directives.graphqls from the graphitron jar before parse, so consumer schemas never re-declare the canonical directives. This is what lets the classifier treat directive presence as ground truth one stage later: the schema loader has already fed every directive declaration into the parsed schema, regardless of whether the consumer’s .graphqls files mentioned them.

  2. Classification is the only place directives are read. GraphitronSchemaBuilder reads each directive once and resolves everything the generator needs into typed model values: table names, column references, method names, extraction strategies, batch keys. Generators downstream see the classified model and never touch directive syntax. The boundary keeps the model "what to emit," never "what to interpret."

  3. The writer’s idempotency contract is unconditional. On every run, JavaFile.writeToPath writes only files whose rendered content differs from disk (SHA-256 comparison) and deletes orphans in rewrite-owned sub-packages. Both halves run on every emit, not just full builds; this is what keeps the dev-loop’s IDE-recompile times proportional and what stops a delete-a-type cycle from leaving stale files behind. Pinned by IdempotentWriterTest and GeneratorDeterminismTest.

The Code Generation Triggers page is a zoomed-in view of the middle three stages (schema → classified model → generators). This index page names the loader, the validator, the writer’s idempotency contract, and the consumer compile that closes the loop.

Modules

graphitron-rewrite/ is a nested monorepo with its own parent pom (graphitron-rewrite-parent, 10-SNAPSHOT). Nine modules cover the generator, its inputs, its consumers, and the tooling that wraps both ends:

Module Purpose

graphitron-javapoet

Internal fork of Square JavaPoet; the emit-time API every generator builds through.

graphitron

The generator core: schema loader, classifier, validator, and every generator.

graphitron-fixtures-codegen

Builds the test database and runs jOOQ codegen against it.

graphitron-sakila-db

Packages those generated jOOQ classes (Sakila-inspired catalog plus the nodeidfixture and idreffixture sub-schemas) as a jar that downstream tests depend on.

graphitron-sakila-service

@service / @externalField / @condition implementations referenced from the example schemas (FilmService, SampleQueryService, …​). Compile-scope dep on graphitron-sakila-db for the jOOQ tables.

graphitron-maven-plugin

Maven plugin: generate, validate, and dev Mojos (the dev mojo provides the watch loop).

graphitron-sakila-example

End-to-end consumer: compiles emitted Java against a real jOOQ catalog, executes it against Postgres, and serves a runnable Quarkus + JAX-RS reference application from the same module.

graphitron-lsp

Editor LSP server for .graphqls authoring.

roadmap-tool

Regenerates graphitron-rewrite/roadmap/README.md from per-item front-matter.

Per-module READMEs are deliberately not maintained; this table is the orientation surface, and lives next to the architecture pages so it stays in sync with the pipeline they describe.

Publishing

Trunk runs at 10-SNAPSHOT; releases are cut from tag-driven GitHub Releases. The .github/workflows/maven-publish.yml workflow accepts v<MAJOR>.<MINOR>.<PATCH> and v<MAJOR>.<MINOR>.<PATCH>-RC<n>, sets the version across the rewrite reactor, signs (sources + javadoc + GPG), and pushes to Maven Central via the central-publishing-maven-plugin with autoPublish=true. Maven version ordering treats 10.0.0-RC1 as strictly less than 10.0.0, so consumers asking for [10.0.0,) won’t pick up RCs by accident. Snapshots aren’t published; the rewrite parent declares no <snapshotRepository>, so an accidental mvn deploy on 10-SNAPSHOT fails fast.

Publishable surface: graphitron-javapoet, graphitron, graphitron-lsp, graphitron-maven-plugin. Test fixtures and example consumers (graphitron-fixtures-codegen, graphitron-sakila-db, graphitron-sakila-service, graphitron-sakila-example, roadmap-tool, docs) carry <maven.deploy.skip>true</maven.deploy.skip>.