-
Notifications
You must be signed in to change notification settings - Fork 162
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Async request stream deserialization with System.Text.Json #299
Async request stream deserialization with System.Text.Json #299
Conversation
Bloody hell, how do you make a PR a draft PR once it's not. Sigh. Anyway... this is a WIP. I'm kinda thinking this might be all that's required to avoid the IIS/Kestrel setting as it's probably just choking on the stream of the request body being read syncly, but I'll find out soon enough. Oustanding:
|
Thanks for step forward. For me, the main question is whether to support another serializer in-place or with external package. You have now linked the choice of serializer to target platform. What if I prefer to use old serializer in netcore3.0 app ? I may want to do this due to some specific settings available to me only in Also regarding graphql-dotnet/graphql-dotnet#1448. After merging it we should decide how to deal with APIs like |
I am considering this option (message text is approximate): public static IGraphQLBuilder AddGraphQL(this IServiceCollection services, Func<IServiceProvider, GraphQLOptions> options)
{
services.TryAddSingleton<IDocumentExecuter, DocumentExecuter>();
services.TryAddTransient(typeof(IGraphQLExecuter<>), typeof(DefaultGraphQLExecuter<>));
services.AddSingleton(p => Options.Create(options(p)));
services.TryAddSingleton<IDocumentWriter>(x =>
{
throw new InvalidOperationException("IDocumentWriter not set in DI. Add one of IDocumentWriter implementation, for example GraphQL.NewtonsoftJson.DocumentWriter or GraphQL.SystemTextJson.DocumentWriter");
});
return new GraphQLBuilder(services);
} Thus, we provide freedom of action to the caller. We have no dependency on serializer packages. But at the same time, we retain (and clearly indicate) the need for at least some kind of implementation to work further. |
@sungam3r , I've got this working now and passing tests. You're right, we're taking on a specific serializer for netcoreapp3.0+ and not giving people choice. I'm not sure if that's a big deal though for this PR, where I'm only fixing up the sync read. My reasoning: it's not like the deserialization needed changes. We're adhering to the GraphQL spec, which is camelCase JSON. So, do we really need to provide consumers with options of a serializer?
I'm thinking really we should be the ones making the choice here, which essentially boils down to which is the fastest / most supported / easiest to maintain long-term. What do you think @joemcbride? |
That is, to step on the same rake as it was with Newtonsoft.Json ;)
JSON is just a format, Newtonsoft.Json / System.Text.Json / whatever - implementations. You can use any implementation to work with this format.
Why so? This PR essentially claims the opposite. There was one implementation with one set of characteristics; another implementation with a different set of characteristics became.
Yes, but what follows from this? The specification does not say anything about how deserialization should occur.
The best strategy of all time in such cases when you need to choose the fastest / most effective / best solution is not to choose it at all. No need to solve this problem. You just need to put it out of the bracket, giving the choice to the caller. The caller will be more than happy with the opportunity to choose among several out-of-the-box (standard) implementations and the opportunity to create his own.
My intuition says YES. |
…r the caller to choose from.
Gonna call it a night. Hopefully this has set us up along a decent path though. Can you have a think about how you'd want the tests amd Samples.Server Startup to look like? Now that we've got two different pluggable serializers, I guess we need to make sure we're testing them. I'm thinking we can just pass through a config value from the tests that tells the Startup to toggle between deserializers. Should be easy enough. |
Ok. Also you can add command args in profiles for serializers in |
Update sample middleware implementation. Reverse ternary operation for readability.
I again looked at the changed files. As I understand it, there are several cosmetic changes left in the documentation and code. In addition, you were going to do more tests. |
Also please look at graphql-dotnet/graphql-dotnet#1541 |
LGTM :) |
Actually wait, I think we can now add Graph type to the test suite too now. |
OK, added. All yours. Surely this is it! LGTM!! |
Let's do it! I've got a branch off this one where I was playing with a benchmark so we can see what the go is. Will rebase it off develop though once this is merged. |
🎉 |
This PR:
GraphQLRequest
behind an interface and provides two implementations; one for legacy (usingNewtonsoft.Json
) and one usingSystem.Text.Json
as the default for netcoreapp3.0+ targets.AllowSychronousIO
is configured to true.