Hi, I have a question regarding Spring graphQL dat...
# server
p
Hi, I have a question regarding Spring graphQL data/error management. I have a use case where I want to return several results, including the error ones, as a Union. something like this:
Copy code
extend type Mutation {
userCreate(): UserCreatePayload
}
union UserCreatePayload = UserCreated | UserAlreadyExists
I have a MutationsResolver that handles the
userCreate
mutation by calling a
UserService
that is transactional. When trying to create a user, if the user already exists, I'm throwing a
UserAlreadyExist
Exception that is handled in the mutation resolver with a try/catch block and then mapped to the UserAlreadyExists type in graphql. The problem is that as the UserService is transactional, whenever I throw the exception, the transaction is marked a rollbackOnly by spring (which is good) and then the graphql flow goes through the DefaultGraphQLErrorHandler that finally return an error to the end user. I would like to have the exactly same behavior except for the graphql error handler returning a GraphqlError. Instead I want to return the
UserAlreadyExists
type I defined in the graphql schema. Is there anyway to do so? (I do not want to use sealed classes instead of exceptions in the service as the code gets dirty) Thanks!
d
which GraphQL server implementation are you using?
p
graphql-java
d
graphql-java
is a GraphQL implementation but doesn't define a server (as that is a higher level concept) -> some libs built on top of
graphql-java
providing server functionality •
graphql-kotlin
(I'm one of the maintainers of it) •
graphql-java-kickstart
netflix-dgs
spring-graphql
*or your own altogether
depending on the server they might be some differences in how you define your resolvers
p
yes.
graphql-java-kickstart
is the one I'm using.
d
I'd assume you could just return the
UserAlreadyExist
from your try/catch block in the reesolver?
i.e. instead of throwing an exception from a resolver just return an object?
p
I'm doing that. The problem is that as spring marked the transaction as rollbackOnly, then the flow goes through the DefaultGraphQLErrorHandler and the end user is getting the graphql error instead of the data
d
sounds like its caused by Spring and not really
graphql-java-kickstart
you probably can create custom exception handler but that would require some custom logic
p
That might help. Thank you. I will let you know if it worked.
Unfortunately this did not work as the return type of the
onException
function is a DataFetcherExceptionHandlerResult and not a DataFetcherResult
I ended up adding the
noRollbackFor = [MyException.class]
to the Transactional annotation. By I'm not sure this is the safer approach.
@Dariusz Kuc Finally I found the issue. My MutationResolver class had a
@transactional
which is conceptually wrong as it is a port adapter. By removing that
@transactional
everything worked as expected. There is no need to use the
noRollbackFor
.Many Regards.
👍 1