GraphQL with Java Spring Boot and Postgres or MySQL made easy! 
Tags: java, graphql, postgres, springboot
Published: 2020-04-09 15:51:14

[GraphQL](https://graphql.org/) is revolutionizing the way developers build APIs. It lets you query precisely what you want. Nothing more, nothing less! It also gives you the flexibility to query related objects in a single round trip, unlike the REST APIs. 

In this blog post, I am going to introduce [GraphQLize](https://www.graphqlize.org/), a JVM library for developing GraphQL API server instantly from any Postgres and MySQL databases. 

## Why GraphQLize?

In a nutshell, it aims to simplify the effort required to expose GraphQL APIs over relational databases. 

In the JVM ecosystem, developing GraphQL APIs to expose the data from the relational databases requires a lot of manual work. Right from defining the GraphQL schemas (either code-first or schema-first) to wiring them with resolvers and the database access logic, we spend a significant amount of our development time.

In addition to this, we also need to take care of optimizing the underlying SQL queries to avoid problems like N+1 queries. We have to account the maintenance of the resulting codebase as well!

GraphQLize will help you to overcome all these shortcomings. It provides you with an efficient GraphQL implementation in just a few lines of code.

## What is GraphQLize?

GraphQLize is a JVM library written in Clojure with Java interoperability. The crux of GraphQLize is generating the GraphQL schema and resolving the queries by making use of JDBC metadata provided by the JDBC drivers.

It currently supports Postgres (9.4 & above) and MySQL (8.0 & above).

## Getting Started

One of the core design goals of GraphQLize is not to tie to any web development framework and remain as a drop-in JVM library in any JVM languages like Java, Scala, Clojure or Kotlin. 

Getting started with GraphQLize is simple and involves only a few steps.

* Add the GraphQLize dependency in your project.
* Initialize GraphQLize Resolver by providing the Java [SQL data source](https://docs.oracle.com/javase/7/docs/api/javax/sql/DataSource.html).
* Add a GraphQL API endpoint and use the initialized GraphQlize Resolver in the previous step.

The actual implementation of these steps will vary based on which language (Java, Kotlin, Clojure, Scala) and framework (Spring Boot, Ktor, Pedestal, Scalatra, etc.). 

In this blog post, we are going to look at how to use GraphQLize in a Java spring-boot project to build a GraphQL API. 

## Getting Started With Spring Boot

As we typically do, let's go to [Spring Initializr](https://start.spring.io/) and create a Java project with Web & JPA as dependencies. This documentation uses this [Spring Initializr template](https://start.spring.io/#!type=gradle-project&language=java&platformVersion=2.2.5.RELEASE&packaging=jar&jvmVersion=1.8&groupId=org.graphqlize.java&artifactId=spring-boot&name=spring-boot&description=Demo%20project%20for%20Spring%20Boot%20and%20GraphQLize&packageName=org.graphqlize.java.spring-boot&dependencies=web,data-jpa).

### Adding Dependencies

The first step is to add the `graphqlize-java` & the JDBC driver dependencies.

```groovy
// ...
repositories {
	// ...
	maven { url "https://clojars.org/repo" }
}

dependencies {
  implementation 'org.graphqlize:graphqlize-java:0.1.0-alpha7'

  // For Postgres
  implementation 'org.postgresql:postgresql:42.2.10'

  // For MySQL
  implementation 'mysql:mysql-connector-java:8.0.19'

  // ...
}
```

### Initializing GraphQLizeResolver

The next step is initializing `GraphQLizeResolver`. To do it, let's a create new file _GraphQLizeResolverProvider.java_ and add the following code to expose the `GraphQLizeResolver` as a spring-boot bean.

```java
package org.graphqlize.java.springboot;

import org.graphqlize.java.GraphQLizeResolver;
import org.springframework.context.annotation.Bean;
import org.springframework.stereotype.Component;

import javax.sql.DataSource;

@Component
public class GraphQLizeResolverProvider {
  private final DataSource dataSource;
  private final GraphQLizeResolver graphQLizeResolver;

  public GraphQLizeResolverProvider(DataSource dataSource) {
    this.dataSource = dataSource;
    graphQLizeResolver = new GraphQLizeResolver(dataSource);
  }

  @Bean
  public GraphQLizeResolver graphQLizeResolver() {
    return this.graphQLizeResolver;
  }
}
```

During initialization, the `GraphQLizeResolver` reads the metadata of the database using the JDBC metadata APIs and keeps an in-memory representation of them.

### Configuring DataSource

To configure the `DataSource`, let's add the following properties in the _application.properties_ file.

**For Postgres**,
```
spring.datasource.url=jdbc:postgresql://localhost:5432/sakila
spring.datasource.username=postgres
spring.datasource.password=postgres
```

**For MySQL**,
```
spring.datasource.url=jdbc:mysql://localhost:3306/sakila
spring.datasource.username=root
spring.datasource.password=mysql
```

> Make sure you are changing the above values to refer your database connection. The above example assumes that you are using the _sakila_ database created from this [JOOQ's example repository](https://github.com/jOOQ/jOOQ/tree/master/jOOQ-examples/Sakila).

## Adding GraphQL Endpoint

The final step is exposing an API endpoint for handling the GraphQL request. To do it, let's create a new file _GraphQLController.java_ and do the following. 

* Create a POJO `GraphQLRequest` for deserializing GraphQL request from the client.
* Create a Controller class with a `GraphQLResolver` dependency. 
* Create a method inside this class to handle the GraphQL request. 

```java
package org.graphqlize.java.springboot;

import org.graphqlize.java.GraphQLResolver;
import org.springframework.http.*;
import org.springframework.web.bind.annotation.*;
import java.util.Map;

class GraphQLRequest {
  private String query;
  private Map<String, Object> variables;

  // ... Getters & Setters are ignored for brevity
}

@RestController
public class GraphQLController {
  private final GraphQLResolver graphQLResolver;

  public GraphQLController(GraphQLResolver graphQLResolver) {
    this.graphQLResolver = graphQLResolver;
  }

  @PostMapping("/graphql")
  public ResponseEntity handle(@RequestBody GraphQLRequest graphQLRequest) {

    String result = 
      graphQLResolver.resolve(
        graphQLRequest.getQuery(), 
        graphQLRequest.getVariables());

    return ResponseEntity.ok()
            .header(HttpHeaders.CONTENT_TYPE, "application/json")
            .body(result);
  }
}
```

Handling the GraphQL request is as simple as highlighted above. 

Get the query & the variables from the request and invoke the `resolve` method on the initialized instance of `GraphQLizeResolver`. 

It returns the `result` as stringified JSON, and we are sending it as response body with the content type as `application/json`. 

### Test Drive

To a test drive of this implementation, start the server and hit the endpoint via curl.

```bash
> curl -X POST \
  --data '{"query": "query { actorByActorId(actorId: 1){firstName}}"}' \
  -H "Content-Type: application/json" \
  http://localhost:8080/graphql
```

You'll get a response like below.

```json
{
  "data": {
    "actorByActorId": {
      "firstName": "PENELOPE"
    }
  }
}
```

### GraphQL Playground and Voyager

With the GraphQL endpoint up and running, the next step is introspecting the GraphQL schema and try out some more queries. 

To introspect, we are going to make use of [Voyager](https://github.com/APIs-guru/graphql-voyager), a tool to visualize GraphQL API as an interactive graph. Adding it to our project is easy thanks to [static content serve capability](https://spring.io/blog/2013/12/19/serving-static-web-content-with-spring-boot) of Spring Boot. 

All you need to do is download this [voyager.html](https://github.com/graphqlize/graphqlize-demo/blob/master/java/spring-boot/src/main/resources/static/voyager.html) file and put it under the _src/main/resources/static_ directory. 

When you restart the server, the Voyager will be available at _http://localhost:8080/voyager.html_. A sample output would look like [this](https://www.graphqlize.org/html/sakila-voyager.html).

Then to interact with the GraphQL API, let's add the [GraphQL Playground](https://github.com/prisma-labs/graphql-playground). Like Voyager, download this [playground.html](https://github.com/graphqlize/graphqlize-demo/blob/master/java/spring-boot/src/main/resources/static/playground.html) file and put in the _static_ directory. 

This GraphQL playground will be available at _http://localhost:8080/playground.html_ after server restart. 

![](https://www.graphqlize.org/img/graphql-playground.png)

## Next Steps

Congrats! You are on course to build impressive applications using GraphQLize in less time. To save yourself some more time, do refer [this documentation](https://www.graphqlize.org/docs/graphql_schema/types-and-fieldss) to know more about how GraphQLize generates the GraphQL schema and the queries. 

The sample code is available in [this GitHub Repository](https://github.com/graphqlize/graphqlize-demo/tree/master/java/spring-boot).

## Summary

In this blog post, we experience a glimpse of how GraphQLize can simplify your efforts in creating GraphQL API to expose the data from Postgres or MySQL. 

GraphQLize is at its early stages now and lacks some critical features to call it production-ready. In the next few months it should be ready for real-world use cases. 

You can keep track of the progress by

* Following the [GraphQLize Twitter account](https://twitter.com/graphqlize).
* Joining [GraphQLize's Discord](https://discord.gg/akkdPqf).
* Subscribing to [GraphQLize's newsletter](https://tinyletter.com/graphqlize-org).

⭐️ If you like GraphQLize, give it a star on [GitHub](https://github.com/graphqlize/graphqlize)! ⭐️