graphql-hive / graphql-hive/envelop
Create a more performant alternative to `onResolverCalled`
- Dominant language
- No language data
- Stars
- 827
- Forks
- 132
- PR merge metrics
- No merged PRs in 30d
Description
**Is your feature request related to a problem? Please describe.**
Currently, any plugin that uses `onResolverCalled` is probably incurring significantly more performance overhead than is necessary.
Many plugins that need to augment resolver behavior need to do this conditionally (on some subset of fields), and even those that wrap every field (like the various tracing plugins) probably should have a way to filter the fields they are wrapping/tracing.
The current approach introduces potentially hundreds of additional `await`s into simple synchronous resolvers per requests. Promises and async/await are very efficient, but in testing I did in Pothos, introducing async wrappers around every resolver in conjunction with async_hooks can easily reduce throughput under load by an order of magnitude.
**Describe the solution you'd like**
For many plugins a lot of logic can be moved from resolve time to an earlier point when the schema is being built.
Adding a new hook like `onResolverDefinition` or something similar that is passed the field definition and returns a `OnResolverCalledHook` would allow plugins to conditionally add hooks on a per-field basis. This could be added without removing the existing `onResolverCalled`, with `OnResolverCalledHook`s being merged when the field is configured and plugins could be migrated to the new API as needed.
This has the additional benefit of pre-comuting values based on directives or extensions on the field to create a wrapper specific to that field. Eg, a validation plugin could create a validator ahead off time, and only wrap the field if it has a validation directive.
In addition to providing a method to conditionally wrap resolvers, the field wrapper created probably should not be an async function. Writing in a style where you use non-promise results directly rather than always awaiting return values is pretty cumbersome, but for a core library the performance gains are probably worth it (This might be an issue to raise separately)
**Describe alternatives you've considered**
Everything above can also be achieved by side-stepping the `onResolverCalled` hook and just mutating the schema directly, but this kinda defeats the purpose of having the awesome plugin system that envelop provides.
**Additional context**
Contributor guide
No contributing guide indexed for this repository
Assessment
This issue has not been assessed yet.