Spring Boot + GraphQL 才是 API 的未来!

共 5145字,需浏览 11分钟

 ·

2021-11-23 21:20

相关阅读

300本计算机编程的经典书籍下载

AI全套:Python3+TensorFlow打造人脸识别智能小程序

最新人工智能资料-Google工程师亲授 Tensorflow-入门到进阶

Java架构全阶段七期完整

黑马头条项目 - Java Springboot2.0(视频、资料、代码和讲义)14天完整版

Spring核心编程思想


作者:NetWhite

来源:blog.csdn.net/x763795151/article/details/117604505

前言
在浅尝GraphQL一文描述了GraphQL及基本使用,本文提供一个基本示例,描述如何基于spring boot的web项目快速应用。
graphql-java的官方文档:Getting started with GraphQL Java and Spring Boot,提供了相关依赖用以快速配置,但是个人真心不建议使用这个库及相关配置方式来搭建脚手架,在实际开发中,业务比较复杂的时候,会导致需要配置的业务代码比较多也比较繁琐,相对下面这种方式,代码复杂性比较高。
本文提供一种更灵活快捷的方式,在spring boot项目中快速应用开发。使用的依赖也和上面官方提供的都不一样,请注意区分。

快速开始

创建spring boot工程

通过Spring Initializr快速搭建,我选的jdk版本及spring boot版本,如下所示,其它版本未做兼容性测试。搜索公众号互联网架构师后台回复“2T”,获取一份惊喜礼包。
点击下方的Generate按钮:
打开工程结构如下,我将application.properties删除了替换成applicaiton.yml,因为我个人比较喜欢yaml的配置方式:

引入相关依赖

pom.xml配置如下:
"1.0" encoding="UTF-8"?>
"http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
 4.0.0
 
  org.springframework.boot
  spring-boot-starter-parent
  2.4.6
   
 

 com.xuxd
 graphql.demo
 0.0.1-SNAPSHOT
 graphql.demo
 GraphQL Demo project for Spring Boot
 
  1.8
  1.8
  1.8
  UTF-8
  UTF-8
  1.18.20
  11.0.1
  2.8.7
 

 
  
   org.springframework.boot
   spring-boot-starter
  


  
   org.springframework.boot
   spring-boot-starter-web
  


  
   org.springframework.boot
   spring-boot-starter-test
   test
  


  
   org.projectlombok
   lombok
   ${lombok.version}
   provided
  


  
   com.graphql-java-kickstart
   graphql-java-tools
   ${graphql-java-tools.version}
  


  
   com.google.code.gson
   gson
   ${gson.version}
  

 


 
  
   
    org.springframework.boot
    spring-boot-maven-plugin
   

  

 



初始化GraphQL实例

我们将创建一个GraphQL实例并将其注册到spring容器中,代码如下。
创建一个GraphQLProvider类:搜索公众号互联网架构师后台回复“2T”,获取一份惊喜礼包。
@Component
public class GraphQLProvider {

    private GraphQL graphQL;

    @Autowired
    private IItemService itemService;

    @Bean
    public GraphQL graphQL() {
        return graphQL;
    }

    @PostConstruct
    public void init() throws IOException {
        GraphQLSchema graphQLSchema = SchemaParser.newParser()
            .file("graphql/base.graphqls")
            .resolvers(new Query(), new Mutation())
            .file("graphql/item.graphqls")
            .resolvers(new ItemResolver(itemService))
//            .file("book.graphqls")
//            .resolvers(new BookResolver())  //其它定义照上面的示例,继续增加
            .build().makeExecutableSchema();

        this.graphQL = graphQL.newGraphQL(graphQLSchema).build();
    }

}
关于*.graphqls或者对应的Resolver如ItemResolver,可以参看浅尝GraphQL相关描述,这里只是作了微调整,相关代码如下:
base.grqphqls
schema {
    # 查询
    query: Query
    # 更新
    mutation: Mutation
}

type Query {
    version: String
}

type Mutation {
    version: String
}
item.graphqls
# 定义一个查询类型
extend type Query {
    queryItemList: ItemList  # 定义查询项目列表
    queryById(id: ID): Item
}

extend type Mutation {
    updateName(param: Param): Item
}

# 定义项目字段
type Item {
    id: ID!
    code: String!
    name: String!
}

type ItemList {
    itemList: [Item!]!  #获取项目列表
    total: Int!      # 获取项目总数
}

input Param {
    id: ID!
    name: String!
}
ItemResolver
public class ItemResolver implements GraphQLQueryResolver, GraphQLMutationResolver {

    private IItemService itemService;

    public ItemResolver(IItemService itemService) {
        this.itemService = itemService;
    }

    // 对应item.graphqls里的queryItemList
    public ItemList queryItemList() {
        return itemService.queryItemList();
    }

    public Item queryById(Long id) {
        return itemService.queryById(id);
    }

    public Item updateName(Param param) {
        return itemService.updateName(param);
    }
}
相关业务代码比较多,就不一一贴了。

提供API

我们需要暴露一个接口来接收请求,并作相关处理,也只需提供一个接口即可。因此我们创建一个Controller:GraphqlController.
 result = new HashMap<>();        ExecutionResult executionResult = graphQL.execute(executionInput);        List errors = executionResult.getErrors();        if (errors != null && !errors.isEmpty()) {            result.put("errors", errors);            return result;        }        return executionResult.getData();    }}" tab="innerlink" data-linktype="2" wah-hotarea="click" style="outline: 0px; -webkit-tap-highlight-color: rgba(0, 0, 0, 0); cursor: pointer; max-width: 100%; box-sizing: border-box !important; overflow-wrap: break-word !important;">@RestController
@RequestMapping("/graphql")
@Log
public class GraphqlController {

    @Autowired
    private GraphQL graphQL;

    @PostMapping
    public Object execute(@RequestBody GraphqlRequest request) {
        ExecutionInput executionInput = ExecutionInput.newExecutionInput()
            .query(request.getQuery())
            .variables(request.getVariables())
            .build();
        Map result = new HashMap<>();

        ExecutionResult executionResult = graphQL.execute(executionInput);
        List errors = executionResult.getErrors();

        if (errors != null && !errors.isEmpty()) {
            result.put("errors", errors);
            return result;
        }
        return executionResult.getData();
    }
}
到这一步,其实基本功能都已配置完成,可以启动项目进行相关测试了。
整个项目的代码结构如下,我尽量用了一个比较常规的web项目结构(controller,service,dao等):

测试

示例中总共提供了3个接口,两个查询一个更新,分别进行测试:搜索公众号互联网架构师后台回复“2T”,获取一份惊喜礼包。
ItemList queryItemList();

Item queryById(Long id);

Item updateName(Param param);
查询所有项目列表(只获取每个项目的编码和名称,以及列表总数):
根据ID查询,获取项目的id和名称
更新指定ID的项目名称
我们项目Id为1编码为test的项目修改为“java项目”
再查询一下,可以看到结果更新了:

结束语

这样整个项目的GraphQL相关的基本配置已经完成,可以进行业务开发了。

全栈架构社区交流群

 「全栈架构社区」建立了读者架构师交流群,大家可以添加小编微信进行加群。欢迎有想法、乐于分享的朋友们一起交流学习。

扫描添加好友邀你进架构师群,加我时注明姓名+公司+职位】

看完本文有收获?请转发分享给更多人


往期资源:


Flutter 移动应用开发实战 视频(开发你自己的抖音APP)
Java面试进阶训练营 第2季(分布式篇)
Java高级 - 分布式系统开发技术视频
浏览 20
点赞
评论
收藏
分享

手机扫一扫分享

分享
举报
评论
图片
表情
推荐
点赞
评论
收藏
分享

手机扫一扫分享

分享
举报