xuorig / chromatophore

GraphQL Continuous Evolution

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Could this work better with a code first approach?

jensneuse opened this issue · comments

Cool idea! Have you thought about implementing this in a code-first approach instead of schema-first?
E.g. allow the developer to "overload" a resolver with a version tag (or similar).
The client can send a Version Header (or similar) if they want to pin it to an old version.
Oops, we're introducing versioning to GraphQL...

So, with a code-first approach, you don't have to create priceV2, priceV3, etc.. and no additional directives are required, just implement multiple resolvers, deprecate the old ones, but keep old resolvers existent to not break old clients.

Yep this would be very nice with a code-first approach 💯 I went with SDL-first because spring-graphql and dgs-framework both favor this approach, but in theory I 100% agree with you.

So, with a code-first approach, you don't have to create priceV2, priceV3, etc.. and no additional directives are required, just implement multiple resolvers, deprecate the old ones, but keep old resolvers existent to not break old clients.

One thing I'll note though is that it would require more than just resolver overrides, since the goal is also to modify the field definition itself. Redefining the type, arguments etc. With code first we could design a more interesting API but in the end it may have to create new definitions and annotate them with metadata (potentially directives depending on metadata support of the underlying library)

One thing we're working on at WunderGraph is to solve this problem at the Gateway layer. Simply break your contract if you want. No change in the GraphQL framework is required. We force all clients to "register" their operations at deployment time, so their "version" of the contract is already pinned. When you break the GraphQL API, we detect this and generate a middleware which you can implement. This way, you can continuously evolve (and break) your API, and the framework makes sure that old clients, pinned to old versions, talk to a middleware that "migrates" their API call on the request and response path.

I think we're trying to solve similar problems. Your approach is to embed it into a framework, I'm trying to find a generic solution that works with all frameworks out of the box.

I'm curious what you think on this approach.