-
Notifications
You must be signed in to change notification settings - Fork 48
client_subscription
The client mode makes it easy for a Java GraphQL client-side application, to execute subscriptions against a GraphQL server. The graphql-maven-plugin generates all the necessary code, so that a Java application can call a GraphQL server by simply calling the relevant Java method.
Since v1.14, subscriptions work with both Partial Request and Full Requests. You'll find the differences between Full and Partial requests on the client FAQ and the client page.
As for queries and mutations, subscription can be executed in two ways:
- The direct execution: you call the generated method with the GraphQL request (partial or full), and you receive the result into Java objects. This is simpler, but slower: for technical reasons, the plugin has two analyze the content of the request.
- As Subscription is usually executed once, the direct execution is the recommended way to execute subscriptions.
- The prepared execution:
- A
GraphQLRequest
object is created by the application, if possible at application startup. This allows to analyze the request only once. And it avoids errors during the app execution, as all the GraphQL requests have been checked at startup. - Each GraphQL request execution is executed from this object.
- A
Both kinds of requests, and both modes of execution allows to use bind parameters into your query definitions.
First, you'll have to create or get your GraphQL schema. The GraphQL plugin expects a .graphqls file. See the GraphQL schema doc for all the details.
Then, add the plugin to your Maven POM file, as described in the client page.
Since v1.14, you can execute subscriptions with full requests. The main advantage is that it allows you to use GraphQL variables.
Here is a sample:
@Component
public class SubscriptionRequests {
@Autowired
SubscriptionExecutor subscriptionExecutor;
GraphQLRequest subscriptionRequest;
// Let's prepare the request, once the bean is ready (and the autowired attributes have been set by Spring)
@PostConstruct
public void init() {
subscriptionRequest = subscriptionExecutor.getGraphQLRequest(
"subscription sub($boardNameParam: String!) {subscribeToNewPost(boardName: $boardNameParam){}}");
getSubscribeToNewPostGraphQLRequest("{id date author publiclyAvailable title content}");
}
public SubscriptionClient execSubscription(SubscriptionCallback<Post> callback, String boardName)
throws GraphQLRequestPreparationException, GraphQLRequestExecutionException, IOException {
// Execution of the full request, with one GraphQL Variable: boardNameParam (as defined in the above query)
// Then you can provide the list of parameters, by pair: the parameter's name then its value, here: "boardNameParam", boardName
return subscriptionRequest.execSubscription(callback, Post.class, "boardNameParam", boardName);
}
}
The callback
is an instance of [SubscriptionCallback<Post>](https://github.com/graphql-java-generator/graphql-maven-plugin-project/blob/master/graphql-java-runtime/src/main/java/com/graphql_java_generator/client/SubscriptionCallback.java)
. This callback will receive all the notifications for this subscription, especially:
-
onMessage(T t)
, will be called for each received message from the subscription. In our sample, T is aPost
-
onClose(int statusCode, String reason)
when the subscription is closed -
onError(Throwable cause)
when an error occurs
In each query/mutation/subscription class, the plugin also generates Xxxx and XxxxWithBindValues methods, where Xxxx is successively each query/mutation/subscription defined in this query/mutation/subscription object.
In these methods:
- The query/mutation/subscription parameters (as defined in the GraphQL schema) become parameters of the relevant generated java methods. So you don't need to define and map bind parameters for them.
- But you can still use bind parameters for input parameters of the fields you request, of course
- The subscription methods return an instance of SubscriptionClient.
- This interface has only one method: unsubscribe(), which allows to unsubscribe from this subscribed subscription. This frees resources on both the client and the server, and the network of course.
Below is a sample of the client code:
@Component
public class SubscriptionRequests {
@Autowired
SubscriptionExecutor subscriptionExecutor;
GraphQLRequest subscriptionRequest;
// Let's prepare the request, once the bean is ready (and the autowired attributes have been set by Spring)
@PostConstruct
public void init() {
subscriptionRequest = subscriptionExecutor.getSubscribeToNewPostGraphQLRequest
("{id date author publiclyAvailable title content}");
}
public SubscriptionClient execSubscription(PostSubscriptionCallback callback)
throws GraphQLRequestPreparationException, GraphQLRequestExecutionException, IOException {
// Execution of a partial request. The subscribeToNewPost has one parameter: boardName. This parameter is
// expected from the subscribeToNewPost, as this is a partial request.
return subscriptionExecutor.subscribeToNewPost(subscriptionRequest, callback, "Board name 1");
}
}
The subscription specific part is the creation of the callback. The code for the PostSubscriptionCallback class used in the above sample is available on github.
Of course, you can use bind variables, as with queries and mutations.
If you don't want to store the GraphQLRequest, you can avoid that, by using direct queries. The overhead that exists at each execution is not an issue here, as you'll probably execute the subscription only once.
You still need to provide the callback, that'll receive the notifications you've subscribed to.
Here is a sample with the bind parameters value given as method parameters:
@Component
public class SubscriptionRequests {
@Autowired
SubscriptionExecutor subscriptionExecutor;
public SubscriptionClient subscribe(PostSubscriptionCallback<Post> postSubscriptionCallback) {
// The subscription request accepts one parameter. If you don't want to provide it, you can give it the null value
return subscriptionExecutor.subscribeToNewPost("{id date author publiclyAvailable title content}", postSubscriptionCallback, "Board name 1");
}
}
Creating a first app (non spring)
Connect to more than one GraphQL servers
Easily execute GraphQL requests with GraphQL Repositories
Access to an OAuth2 GraphQL server
How to personalize the client app
Howto personalize the generated code
Client migration from 1.x to 2.x
Implement an OAuth2 GraphQL server
Howto personalize the generated code
Server migration from 1.x to 2.x