从graphql-java-kickstart迁移至Spring Graphql:如何实现依赖共存逐步迁移?
迁移期间让graphql-java-kickstart与Spring GraphQL共存的方案及上下文冲突解决
可以实现两者共存并逐步迁移解析器,但必须做好组件隔离,否则会出现上下文、Schema、请求路由等冲突。以下是具体的解决步骤:
1. 隔离HTTP请求端点
两者默认都使用/graphql作为请求路径,会直接导致请求路由冲突。给其中一方配置独立路径即可:
- 给graphql-java-kickstart指定旧路径:
graphql: servlet: mapping: /legacy-graphql - 给Spring GraphQL指定新路径:
spring: graphql: path: /new-graphql
2. 隔离GraphQL上下文(Context)
两者的GraphQLContext属于不同包:
- graphql-java-kickstart:
com.graphql.spring.boot.execution.GraphQLContext - Spring GraphQL:
org.springframework.graphql.execution.GraphQLContext
要确保各自的解析器只使用对应包的上下文,同时自定义上下文构建逻辑避免混淆:
针对graphql-java-kickstart
自定义上下文构建器,确保老解析器拿到的是kickstart的上下文:
@Component public class LegacyContextBuilder implements GraphQLContextBuilder { @Override public GraphQLContext build(HttpServletRequest request, HttpServletResponse response) { GraphQLContext context = new GraphQLContext(); // 填充老服务需要的上下文数据,比如用户信息、请求头 context.put("authUser", request.getAttribute("authUser")); return context; } // 按需实现其他重载方法 }
针对Spring GraphQL
通过配置类自定义上下文,确保新解析器使用Spring的上下文:
@Configuration public class NewGraphQLConfig { @Bean public GraphQlSourceBuilderCustomizer contextCustomizer() { return builder -> builder.configureRuntimeWiring(wiring -> wiring.addDataFetcher("migratedField", environment -> { org.springframework.graphql.execution.GraphQLContext springContext = environment.getGraphQlContext(); // 使用Spring上下文处理业务逻辑 return springContext.get("authUser"); }) ); } }
3. 隔离Schema与解析器
不要让两者共享Schema文件,避免字段冲突:
- 给graphql-java-kickstart指定老Schema路径:
graphql: servlet: schema-locations: classpath:legacy-graphql/**/*.graphqls - 给Spring GraphQL指定新Schema路径:
spring: graphql: schema: locations: classpath:new-graphql/**/*.graphqls
迁移时,每次只将一个解析器和对应的Schema字段从老服务移到新服务,确保老服务只处理剩余的未迁移字段。
4. 处理依赖版本冲突
两者都依赖graphql-java核心库,版本不一致会导致类加载异常。通过Maven/Gradle统一版本:
Maven示例
<dependency> <groupId>com.graphql-java-kickstart</groupId> <artifactId>graphql-spring-boot-starter</artifactId> <version>12.0.0</version> <exclusions> <exclusion> <groupId>com.graphql-java</groupId> <artifactId>graphql-java</artifactId> </exclusion> </exclusions> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-graphql</artifactId> <version>3.2.0</version> </dependency> <!-- 统一graphql-java版本 --> <dependency> <groupId>com.graphql-java</groupId> <artifactId>graphql-java</artifactId> <version>21.0</version> </dependency>
总结
通过端点、上下文、Schema的三重隔离,就能实现逐步迁移:每次迁移一个解析器到Spring GraphQL,同步更新对应的Schema字段,直到所有业务逻辑都切换到新服务后,再移除graphql-java-kickstart的依赖。
内容的提问来源于stack exchange,提问作者Mohamed Ayman Naguib
相关产品推荐
相关产品推荐

