本文介绍如何在 React 项目中使用 GraphQL 查询,同时配合 @graphql-codegen/cliopen in new window 代码自动生成工具提高开发效率。
初始化项目
初始化和安装依赖
我们使用 create-react-appopen in new window 来初始化前端项目,使用官方的 typescriptopen in new window 模板。
假设我们的项目名称是 bff-graphql-clientopen in new window
yarn create react-app bff-graphql-client --template typescript
等待几分钟后,项目初始化完成。
现在我们安装 GraphQL 的包。
yarn add graphql
由于 graphqlopen in new window 这个包使用起来非常繁琐,我们通过 @graphql-codegen/cli 来自动生成这些类型代码,我们只需要编写查询的 Query
即可。
yarn add -D @graphql-codegen/cli
我们使用 Apollo 客户端来实现查询,同时添加一些 typescript 插件来生成 typescript 代码。
yarn add -D @graphql-codegen/typescript @graphql-codegen/typescript-operations @graphql-codegen/typescript-react-apollo
yarn add @apollo/client
2
3
配置文件
安装完依赖包以后,我们通过 GraphQL Code Generator 的指引来生成配置文件,GraphQL Code Generator 会根据这个配置文件来生成代码。
yarn graphql-codegen init
根据命令行提示,我们生成配置文件。
在生成的配置如下:
overwrite: true
schema: "http://localhost:3000/graphql" # graphql 服务的地址
documents: "src/**/*.graphql" # 查找项目中所有已 .graphql 结尾的文件,来生成代码
generates:
src/generated/graphql.tsx: # 代码输出地址
plugins:
- "typescript"
- "typescript-operations"
- "typescript-react-apollo"
./graphql.schema.json:
plugins:
- "introspection"
2
3
4
5
6
7
8
9
10
11
12
因为我们要使用 Apollo 的客户端,同时使用 React Hook,因此需要对配置做一些修改:
overwrite: true
schema: "http://localhost:3000/graphql"
documents: "src/**/*.graphql"
generates:
src/generated/graphql.tsx:
plugins:
- "typescript"
- "typescript-operations"
- "typescript-react-apollo"
config:
noComponents: true
noNamespaces: true
skipTypename: true
withHooks: true # 使用 React Hook
withComponent: false
withHOC: false
apolloReactHooksImportFrom: "@apollo/client" # 使用 Apollo Client
apolloReactCommonImportFrom: "@apollo/client"
./graphql.schema.json:
plugins:
- "introspection"
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
相关配置的功能说明可以在这里open in new window找到,就不一一赘述了,这里只标出来比较关键的两个配置。
第一个查询
完成配置以后,我们现在来尝试查一下在上一篇文章中定义的商品信息。
自动化生成查询代码
先启动 GraphQL 服务,打开 playground 看看系统内有哪些模型可查。在上一篇文章中,我们定义了商品模型、订单模型。我们先来查一下商品模型。
我们先在 src
目录下新建一个 graphql
目录,用来存在所有的 .graphql
文件。
query Goods($param: GoodsParam!) {
goodsData(param: $param) {
goodsId
goodsName
}
}
2
3
4
5
6
将上面的内容保存在 src/graphql/goods.graphl
中。运行 yarn codegen
,我们看到命令行显示运行成功,查看 src/generated/graphql.tsx
中生成了很多代码。
我们在生成的代码中看到了这两个函数,我们会用他们来查询商品信息:
export function useGoodsQuery(baseOptions: ApolloReactHooks.QueryHookOptions<GoodsQuery, GoodsQueryVariables>) {
const options = {...defaultOptions, ...baseOptions}
return ApolloReactHooks.useQuery<GoodsQuery, GoodsQueryVariables>(GoodsDocument, options);
}
export function useGoodsLazyQuery(baseOptions?: ApolloReactHooks.LazyQueryHookOptions<GoodsQuery, GoodsQueryVariables>) {
const options = {...defaultOptions, ...baseOptions}
return ApolloReactHooks.useLazyQuery<GoodsQuery, GoodsQueryVariables>(GoodsDocument, options);
}
2
3
4
5
6
7
8
useGoodsQuery
是立即查询,useGoodsLazyQuery
会返回一个函数,调用这个函数才会触发查询。详细信息可以查看这两函数的签名。
每次修改 .graphql
文件都执行一次 yarn codegen
是非常麻烦的。我们来开启 @graphql-codegen/cli
的 watch
模式,来实现自动化生成。
{
"scripts": {
"codegen": "graphql-codegen --config codegen.yml --watch"
},
}
2
3
4
5
此时再执行 yarn codegen
,控制台显示:
使用 ApolloClient
先在 src/index.tsx
中完成 ApolloClient 的初始化和配置。
import { ApolloClient, ApolloProvider, HttpLink, InMemoryCache } from "@apollo/client";
const apolloClient = new ApolloClient({
link: new HttpLink({
uri: "http://localhost:3000/graphql",
}),
cache: new InMemoryCache(),
defaultOptions: {
query: {
errorPolicy: "all",
fetchPolicy: "network-only",
},
watchQuery: {
errorPolicy: "all",
fetchPolicy: "network-only",
},
},
});
ReactDOM.render(
<React.StrictMode>
<ApolloProvider client={apolloClient}>
<App />
</ApolloProvider>
</React.StrictMode>,
document.getElementById("root")
);
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
配置完成后,稍微改造下 App.tsx
,使用 useGoodsQuery
查询数据,并将数据展示出来:
import React from "react";
import { useGoodsQuery } from "./generated/graphql";
function App() {
const { data, loading } = useGoodsQuery({
variables: {
param: {
goodsId: "g-00001",
},
},
});
if (loading) {
return <div className="App">loading data...</div>;
}
return <div className="App">{JSON.stringify(data?.goodsData, null, 4)}</div>;
}
export default App;
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
此时运行 yarn start
,我们可以在浏览器中看到输出的商品信息。
我们可以看到页面先显示 loading data...
然后显示查到的商品信息:
{ "__typename": "GoodsData", "goodsId": "g-0001", "goodsName": "商品名称" }
至此,我们就实现了在 React 项目中使用 GraphQL 查询数据。
总结
本文介绍如何在 React 项目中使用 GraphQL 查询数据。
通过 @graphql-codegen/cli
自动化生成代码,提高开发效率。文中展示了如何编写配置文件来启用 React Hook。
通过 --watch
参数来开启 @graphql-codegen/cli
的监听模式,实现 .graphql
变动自动化生成代码。
同时,我们使用 Apollo Client 来实现 GraphQL 查询,并展示了如何配置 Apollo Client。
关注微信公众号,获取最新推送~
加微信,深入交流~