Open jszwedko opened 4 years ago
For a subscription I saw:
2020/04/24 11:39:31 1 before operation
2020/04/24 11:39:31 1 before field Subscription.todo
2020/04/24 11:39:31 in resolver
2020/04/24 11:39:31 1 after field Subscription.todo
2020/04/24 11:39:31 1 after operation
2020/04/24 11:39:31 1 before response
2020/04/24 11:39:31 1 before field Todo.id
2020/04/24 11:39:31 1 after field Todo.id
2020/04/24 11:39:31 1 after response
2020/04/24 11:39:31 1 before response
2020/04/24 11:39:32 1 before field Todo.id
2020/04/24 11:39:32 1 after field Todo.id
2020/04/24 11:39:32 1 after response
2020/04/24 11:39:32 1 before response
2020/04/24 11:39:33 1 before field Todo.id
2020/04/24 11:39:33 1 after field Todo.id
2020/04/24 11:39:33 1 after response
which seems to call the resolver during the operation middleware execution as opposed to the query
operation which calls it after.
I guess the same problem is affecting the AroundOperation
extension. Unlike AroundResponse
, it is executing the code after next(ctx)
before the operation is actually done, making it useless if you want to execute code right after operations are done.
The problem is that you need to add your logic to the returned function from the interception.
That function will be called when the response is finished. By using defer
you are not in fact waiting for the response.
func InterceptOperation(ctx context.Context, next graphql.OperationHandler) graphql.ResponseHandler {
// Before the operation
handler := next(ctx)
return func(ctx context.Context) *graphql.Response {
response := handler(ctx)
// After each response!
return response
}
}
This was very non-obvious to me as well :). Would be great to have a page in the docs about request lifecycle, operation context, etc
In either case, thank you for the solution @Draiken!
What happened?
This might just be a matter of documentation clarification, but we were using to wrap operations to record timings and other metadata and found that the
next OperationHandler
that is passed in returns before the operation is actually completed.Is this expected behavior?
This was the output when I just added log statements to a handler extension that implements:
For a query:
We can see here that the operation middleware is called and returns before the response middleware starts.
What did you expect?
We expected the handler passed to our operation middleware to not return until the operation finished execution and the response was resolved.
Minimal graphql.schema and models to reproduce
I used
gqlgen init
to create the default models. This is myserver.go
file:And the
schema.resolvers.go
:versions
gqlgen version
?v0.11.0
go version
?go version go1.14.2 linux/amd64