Library / SDK
graphql-java-kickstart/graphql-java-tools avatar
graphql-java-kickstart/graphql-java-tools

graphql-java-tools wires a GraphQL schema to the POJOs you already have

A schema-first tool for graphql-java inspired by graphql-tools for JS

823 stars175 forksKotlinMIT

At a glance

What is it?
graphql-java-tools is a schema-first tool for graphql-java that reads a GraphQL schema, discovers the classes behind it and generates data fetchers for you, so you can expose existing domain objects instead of writing schema builders. It is a Kotlin library published under an MIT licence on a fast 14.x release line.
Who is it for?
Teams with an existing Java or Kotlin service that already has domain classes and want to expose a GraphQL API should adopt graphql-java-tools, because it turns a schema file into a working API without hand written builders or a resolver per field. It is the wrong choice for a greenfield API where you would rather derive the schema from your types, and it is the wrong choice for a service with no JVM domain layer at all.
Can I use it commercially?
Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository received new commits within the last day.
What is it written in?
Mainly Kotlin, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on October 23, 2026, and from our analysis. They are not legal advice.

Editorial analysis

Schema-first means a schema file, not a builder in code

graphql-java-tools exists to let you build a graphql-java schema with the GraphQL schema language instead of code.

The description in the README is that the library allows you to use the GraphQL schema language to build your graphql-java schema. The alternative it sets out to avoid is hard to read builders in code, and the reason the project gives is that describing GraphQL Java objects by hand takes a lot of work and quickly becomes unreadable.

This is not a new GraphQL engine. graphql-java does the executing; this library sits on top of it and handles the wiring between a schema definition and Java classes. The inspiration was graphql-tools for JavaScript, and the project describes itself as inspired by it.

Who it is for is stated plainly in the README. It works well if you already have domain POJOs that hold your data, for example objects you already use for RPC, ORM or REST, because it lets you map those to GraphQL objects. The bring your own object idea is the core of the design: the library parses the schema and you supply the implementations.

The JVM language is not a restriction. The README says the project aims for smooth integration with Java but works for any JVM language, and points at Kotlin as a place to try it. The library itself is written in Kotlin and published as io.github.graphql-java-kickstart:graphql-java-tools.

Discovery starts at Query and Mutation and walks your classes

The interesting part of the design is the discovery process, and the README describes it in a way that explains the whole feature set.

Type to class discovery works like this. GraphQL Java Tools starts from your root objects, Query and Mutation, and as it generates data fetchers for you it starts to learn about the classes you use for a given GraphQL type. There is no registry of type mappings you maintain by hand; the library infers them from the shape of your root objects and the schema.

Generated data fetchers follow from that. The library automatically creates data fetchers for your fields that call the appropriate method on your Java class. The practical consequence is that adding a field to the API means adding the field definition to your schema and adding a corresponding method on your class. Nothing else changes.

Stateful data fetchers exist because of how real services are built. The README notes that if you are using an IOC container such as Spring, it is hard to wire up data fetchers that use beans you have already defined without a pile of fragile configuration. GraphQL Java Tools lets you register resolvers for any type, and a resolver can bring state along and use it to resolve fields. So the automatic path handles the plain data case and the resolver path handles the cases where you need dependency injection.

Because discovery is inference, it can be wrong. The library therefore validates as it builds, which is the subject of a later section.

Class validation happens when the schema is built

There are no compile-time checks on the relationship between a GraphQL type and a Java class, and GraphQL Java Tools makes up for that at runtime.

The README describes two behaviours. The library warns you if you provide classes or types that you do not need, and it errors if you use the wrong Java class for a given GraphQL type when it builds the schema.

That split between warning and error is a design decision worth noting. Extra classes produce noise rather than failure, because a domain object often has more state than the API exposes and trimming it would be tedious. A mismatched class produces a failure, because there is no way to resolve the field.

The error surfaces at schema build time rather than at query time, which is the good outcome. A query hitting an unmapped field deep in a resolver chain is harder to diagnose than a startup failure that names the type and the class it did not like.

Unit testability is the other benefit the README highlights. Since the GraphQL schema is independent of your data model, your classes stay simple and are extremely testable. A service that resolves fields by calling methods on plain objects can be tested without a GraphQL harness at all, and the schema itself can be tested separately once the wiring is done.

Adding it to a Gradle or Maven build

The installation instructions are short, and they say something important about the project: you set a Kotlin version yourself before adding the dependency.

For Gradle, the README tells you to set the Kotlin version in your gradle.properties:

text
kotlin.version=2.3.10

and then add the dependency:

groovy
compile 'io.github.graphql-java-kickstart:graphql-java-tools:14.3.0'

The Maven route sets the same value in the properties section of your pom:

xml
<properties>
    <kotlin.version>2.3.10</kotlin.version>
</properties>

followed by the dependency itself:

xml
<dependency>
    <groupId>io.github.graphql-java-kickstart</groupId>
    <artifactId>graphql-java-tools</artifactId>
    <version>14.3.0</version>
</dependency>

The coordinate is on Maven Central under the io.github.graphql-java-kickstart group, and the version in these examples matches the current release.

Two things to notice. The Gradle snippet uses the older compile configuration rather than implementation, which is what the README shows, so check that against your own build configuration rather than copying it blindly into a modern build. And the Kotlin version is a property you set, not a transitive dependency the library brings, so it is a version you have to keep in step with your own Kotlin setup.

The detailed usage guide lives in the project documentation rather than in the README, which is where you should go next for resolver registration and the root object wiring.

The alternative: graphql-java's own schema-first wiring

The README names the comparison directly, and it is the fairest way to judge this library.

A few libraries exist to ease the boilerplate pain of describing GraphQL Java objects, including graphql-java's built-in schema-first wiring. The claim the project makes about the others is that none of them, so far, do type and datafetcher discovery.

That is the difference in approach, and it is a real one rather than a marketing distinction. Built-in wiring asks you to state the mapping between schema types and classes. GraphQL Java Tools infers it by walking from your Query and Mutation root objects and generating the fetchers as it goes, then validates the result at schema build time. The price of the inference is that mistakes show up as runtime warnings and errors at startup rather than as a compile error, and the price of the explicit approach is that you write and maintain that mapping.

For a service whose domain model is stable and small, stating the mapping by hand is not a burden, and the built-in route keeps you inside graphql-java's own dependency tree. For a service whose types sprawl across a large domain layer, the automatic discovery and the generated fetchers remove considerably more code than they add.

The other alternatives are not GraphQL libraries at all but process choices. Writing a resolver for every field is always possible, and it is the option with the most typing and the most control.

Where graphql-java-tools is the wrong choice

The limits follow from the bring your own object design.

First, the library assumes you have a domain layer. If your service is a thin proxy over a remote API with no meaningful objects of its own, there is nothing to map, and you are back to writing resolvers by hand. The advantage the README claims, reusing POJOs you already have for RPC, ORM or REST, only exists if you have them.

Second, the mapping is inferred, not declared, and the README is direct about the consequence: there are no compile-time checks of the type to class relationship. A schema and a class that disagree will surface as a warning or a schema build error, not as a compiler diagnostic. That is a worse feedback loop than an explicit mapping, and it is the price paid for not writing the mapping down.

Third, the project does not pretend to have no rough edges. It keeps a wiki page titled Known Issues, where the known issues are aggregated, rather than listing them in the README. That is an honest signal, and it is also a signal to read that wiki before you start rather than after you hit a problem.

Finally, the dependency footprint is not trivial for what it does. Pulling in a Kotlin library and a set of resolvers to obtain schema wiring means adding a moving part to your build, on a release line that is shipping minor versions weekly.

An MIT licence and a release line that moves every week

The licence is MIT, with a LICENSE file and a COPYING file at the root of the repository. That is about as permissive as it gets for a library you embed in a commercial service, and it carries the usual notice requirement if you redistribute it.

The release cadence is the thing to plan around. Recent versions are v14.1.0 on 2026-10-03, v14.2.0 on 2026-10-10 and v14.3.0 on 2026-10-18, three minor releases in fifteen days. The repository is not archived and the last push was on 2026-10-22, four days after the latest tag, so the project is being worked on continuously.

A weekly minor release is good news for fixes and a hazard for pinning. Since the library performs type inference at schema build time and validates against your classes, a change in how discovery works can surface as a new warning or a build error in an application that did not change. Pin an exact version in your build, and read the release notes between minor versions rather than tracking latest.

The build itself is Maven based, with a pom.xml at the root of the repository alongside the src tree, a github-build.sh script and a renovate.json for dependency updates. The continuous integration badge points at a snapshot workflow, and the project also hosts a GitHub Discussions space where it explicitly invites people to help with documentation, code and reviews.

One naming detail worth keeping straight: the group id is io.github.graphql-java-kickstart,.

Editorial conclusion

Teams with an existing Java or Kotlin service that already has domain classes and want to expose a GraphQL API should adopt graphql-java-tools, because it turns a schema file into a working API without hand written builders or a resolver per field. It is the wrong choice for a greenfield API where you would rather derive the schema from your types, and it is the wrong choice for a service with no JVM domain layer at all. Before adopting, verify the type to class mapping on your own schema, since the library warns about unused classes and fails at schema build time when a field is bound to the wrong class, and read the known issues wiki before you commit to the 14.x line.

Frequently asked questions

What Maven dependency do I need for graphql-java-tools?

The coordinates are io.github.graphql-java-kickstart:graphql-java-tools at version 14.3.0, and the README also shows the Gradle form. You also set the Kotlin version yourself, kotlin.version=2.3.10, in gradle.properties or in the properties section of your pom.

How does graphql-java-tools map GraphQL types to Java classes?

It starts from your root objects, Query and Mutation, and as it generates data fetchers it learns which classes you use for each GraphQL type. Data fetchers are then created automatically to call the appropriate method on your class, so adding a field means adding it to the schema and adding a matching method.

What happens if I map a GraphQL type to the wrong Java class?

There are no compile-time checks of the type to class relationship, so the library warns you at schema build time if you supply classes or types you do not need, and it errors when you use the wrong Java class for a GraphQL type while building the schema.

How do I use injected Spring beans as data fetchers?

Register resolvers for the types that need them. The README describes resolvers as the way to bring state along and use it to resolve fields, which is the answer to wiring data fetchers that use beans you have already defined in an IOC container.

Official sources

  1. graphql-java-kickstart/graphql-java-tools on GitHub
  2. License: MIT
  3. Project website
  4. README
  5. Releases
Add this badge to your README

If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.

Add this badge to your README

markdown
[![Hysen Labs](https://hysenlabs.com/badge/graphql-java-kickstart-graphql-java-tools.svg)](https://hysenlabs.com/projects/graphql-java-kickstart-graphql-java-tools)

Was this useful?