安装
perl
"@apollo/client": "^3.7.1",
"graphql": "^16.6.0",
@apollo/client
: 这是Apollo Client的JavaScript库,用于在前端应用中管理GraphQL请求。Apollo Client是一个现代化的GraphQL客户端,它提供了强大的功能,包括数据缓存、实时更新、错误处理等。通过Apollo Client,你可以轻松地向GraphQL服务器发出查询和变更请求,并将响应的数据集成到你的前端应用中。版本号^3.7.1表示你的应用使用的是3.7.1版本的Apollo Client库。
graphql
: 这是GraphQL查询语言的JavaScript解析器。GraphQL是一种用于API的查询语言,它允许客户端明确指定需要的数据结构,从而避免了传统REST API中可能存在的数据过载问题。GraphQL库提供了解析GraphQL查询字符串、验证查询的结构等功能。版本号^16.6.0表示你的应用使用的是16.6.0版本的GraphQL库。
这两个库的结合使用, @apollo/client用于发送和管理GraphQL请求,而graphql库则用于解析和验证GraphQL查询语言。在前端应用中,你可以使用Apollo Client来构建和发送GraphQL查询,并使用graphql库来解析从服务器返回的GraphQL响应。这样,你可以通过GraphQL与服务器进行灵活、高效的数据交互,而这两个库的版本号则表示你所使用的具体版本。
vite 支持 eslint
pnpm i vite-plugin-eslint -D
vite-plugin-eslint 是 Vite 构建工具的一个插件,用于集成 ESLint 到 Vite 项目中.
- 代码质量检查: vite-plugin-eslint 可以帮助开发者在构建过程中对项目代码进行静态代码分析,以发现潜在的问题、代码风格不一致或错误。ESLint 是一个常用的 JavaScript/TypeScript 代码质量检查工具,它提供了大量的规则,用于检测和修复代码。
- 自动修复: 除了检查代码,该插件还支持自动修复一些 ESLint 可以处理的问题。通过配置,它可以自动修复一些简单的代码问题,提高开发效率。
- 集成到构建流程: vite-plugin-eslint 能够与 Vite 构建流程集成,确保在开发和生产环境中都能进行代码检查。这有助于在代码提交前或构建过程中发现潜在的问题,提高代码质量。
实现 graphql service 层
pnpm i @apollo/client graphql -S
初始化Apollo Client
新建utlis文件夹,以及apollo.ts,创建Apollo客户端实例。
javascript
import { ApolloClient, InMemoryCache } from '@apollo/client';
export const client = new ApolloClient({
uri: 'http://localhost:3000/graphql',
cache: new InMemoryCache(),
});
import { ApolloClient, InMemoryCache } from '@apollo/client';
: 这行代码引入了Apollo Client库中的ApolloClient和InMemoryCache两个类。ApolloClient用于创建一个Apollo客户端实例 ,而InMemoryCache
是用于客户端内部缓存数据的缓存实现。
InMemoryCache 是 Apollo Client 提供的一种缓存实现,它用于在客户端内部缓存GraphQL查询的响应数据。这个缓存实现的主要作用是在客户端内存中维护一个数据存储,将从服务器获取的数据响应保存在内存中。当应用程序执行相同的GraphQL查询时,它会首先检查内存缓存中是否已经有了该查询的响应数据,如果有则直接返回缓存中的数据,避免了不必要的网络请求。
以下是 InMemoryCache 的主要特性和作用:
- 缓存响应数据: 当应用程序发起GraphQL查询时,InMemoryCache 会将查询的响应数据缓存到内存中。这包括了查询的具体结果以及相应的数据标识(例如ID)。
- 智能合并数据: 当多个组件发起相同查询时,InMemoryCache 会智能地将这些查询的响应数据进行合并。它使用数据标识(通常是ID)来判断哪些数据是相同的,从而避免了数据的冗余存储。
- 快速读取数据: 由于数据保存在内存中,所以从缓存中读取数据非常迅速。这减少了应用程序的加载时间,提高了性能。
- 减少网络请求: 通过在客户端内部缓存数据,可以减少对服务器的网络请求。只有在缓存中没有找到数据时,客户端才会向服务器发起请求。
- 自动化的数据更新: 当应用程序修改了缓存中的数据,InMemoryCache 会自动通知相关的查询组件,以便它们可以重新渲染,并显示最新的数据。
总的来说,InMemoryCache 是 Apollo Client 的核心之一,它帮助应用程序有效地管理和利用从服务器获取的数据,提供了一种高效的方式来处理GraphQL查询的响应数据。
export const client = new ApolloClient({ uri: 'http://localhost:3000/graphql', cache: new InMemoryCache(), });:
这部分代码创建了一个新的Apollo客户端实例。在这个实例中,你配置了两个主要的参数:
- uri: 'http://localhost:3000/graphql': 这个参数指定了GraphQL服务器的URL。Apollo Client将会向这个URL发送所有的GraphQL请求。在这个例子中,GraphQL服务器位于本地机器的端口3000上的'/graphql'路径。
- cache: new InMemoryCache(): 这个参数指定了客户端的缓存实现。InMemoryCache是Apollo Client提供的一种缓存策略,它将在客户端内部缓存GraphQL查询的响应数据,以便在后续的查询中使用。通过使用缓存,可以避免不必要的网络请求,提高应用性能。
export const client: 最后,通过export关键字将创建好的Apollo客户端实例导出,使得其他文件可以引入并使用这个客户端实例来发送GraphQL请求。
总的来说,这段代码的作用是创建了一个Apollo Client实例,配置了GraphQL服务器的URL和缓存策略,使得你的前端应用可以使用这个客户端实例来与GraphQL服务器进行数据交互。
2.包裹ApolloProvider
javascript
import React from 'react';
import ReactDOM from 'react-dom/client';
import { ApolloProvider } from '@apollo/client';
import App from './App';
import './index.css';
import { client } from './utils/applo';
ReactDOM.createRoot(document.getElementById('root') as HTMLElement).render(
<ApolloProvider client={client}>
<App />
</ApolloProvider>,
);
import { ApolloProvider } from '@apollo/client'
;: 这行代码引入了Apollo Client库中的ApolloProvider组件。ApolloProvider是Apollo Client提供的React组件,它用于将Apollo Client的实例传递给React应用的组件树,以便应用程序中的组件可以发起GraphQL查询。
import { client } from './utils/applo';: 这行代码引入了应用程序中用于与GraphQL服务器交互的Apollo Client实例,通常从./utils/applo文件中导出。
<ApolloProvider client={client}>, <App />:
这部分代码使用ApolloProvider组件包裹了应用程序的主组件。ApolloProvider组件接受一个client属性,该属性传递了应用程序与GraphQL服务器通信的Apollo Client实例。通过ApolloProvider,整个应用程序的组件树都可以访问到Apollo Client,可以发起GraphQL查询请求。
通过这段代码,整个React应用程序得以和Apollo Client连接,使得应用程序能够方便地发起GraphQL查询请求,并且将查询的数据集成到React组件中,实现前端与GraphQL服务器的数据交互。
3.定义gql schema
创建文件夹
javascript
import { gql } from '@apollo/client';
export const FIND = gql`
query find($id: String!){
find(id: $id){
name
desc
}
}
`;
这段代码使用了Apollo Client库中的gql函数,它用于定义GraphQL查询。
import { gql } from '@apollo/client'
;: 这行代码引入了Apollo Client库中的gql函数。gql函数是一个用于解析GraphQL查询字符串的函数,它可以将一个字符串转换为GraphQL AST(Abstract Syntax Tree)。
`` export const FIND = gql...` ```: 这部分代码定义了一个GraphQL查询。在这个例子中,定义了一个名为FIND的GraphQL查询,它使用GraphQL模板字符串的语法,包裹了一个具体的查询字符串。这个查询的目的是根据提供的id参数查询特定用户的name和desc字段。
中间的代码可以在GraphQL调试面板复制
javascript
query find($id: String!){
find(id: $id){
name
desc
}
}
query find($id: String!)
: 这行代码定义了一个GraphQL查询操作,命名为find。它接受一个名为id的参数,类型为字符串,表示要查询的用户的唯一标识。$id: String!中的!表示该参数是必需的。
{ find(id: $id) { name desc } }
: 这部分代码指定了查询的具体操作。在find操作中,传入了id参数,并请求返回用户的name和desc字段。这里的name和desc是假设用户对象中包含的字段名。
4.使用useQuery,useMutation
在App.tsx中编写,
此时
javascript
import { useQuery } from '@apollo/client';
import './App.css';
import { FIND } from './graphql/demo';
const App = () => {
const { loading, data } = useQuery(FIND, {
variables: {
id: '22820297-e288-42ba-aadf-3a4062c5c3cb',
},
});
return (
<div>
<p>
data:
{JSON.stringify(data)}
</p>
<p>{`${loading}`}</p>
</div>
);
};
export default App;
上述代码使用了Apollo Client中的useQuery hook,它是一个用于在React函数组件中执行GraphQL查询的钩子函数。
import { useQuery } from '@apollo/client'
;: 这行代码引入了Apollo Client库中的useQuery hook。useQuery hook允许在React函数组件中执行GraphQL查询,并处理查询的结果(例如加载状态、查询数据等)。
import { FIND } from './graphql/demo';
: 这行代码引入了之前定义的GraphQL查询FIND。这个查询通常包含在一个单独的文件中(例如demo.js),然后被引入到应用程序中。
const { loading, data } = useQuery(FIND, { variables: { id: '22820297-e288-42ba-aadf-3a4062c5c3cb', }, });
: 这行代码使用useQuery hook来执行GraphQL查询。useQuery接受两个参数:第一个参数是之前定义的GraphQL查询(在这里是FIND),第二个参数是一个对象,用于传递查询的变量(如果有的话)。
- loading: 这是一个布尔值,表示查询是否仍在加载中。当loading为true时,表示查询尚未完成。
- data: 这是包含查询结果的对象。当查询完成后,data中将包含从服务器返回的数据。
useQuery hook
负责在组件挂载时(或者在查询变量发生变化时)发起GraphQL查询,并将查询的结果返回给组件。variables
选项中指定了查询所需的变量,例如id的值。
通过这种方式,App组件可以根据loading状态显示加载指示器,然后使用data中的数据来渲染应用程序的UI,从而实现了与GraphQL服务器的数据交互和渲染。
运行结果如下:
具体的网络请求信息如下
视频插播
开启跨域限制:
javascript
import { NestFactory } from '@nestjs/core';
import { AppModule } from './app.module';
async function bootstrap() {
const app = await NestFactory.create(AppModule);
app.enableCors();
await app.listen(3000);
}
bootstrap();
如果想允许部分地址可以跨域,需要这么写:
也可以配置的允许跨域的域名:
css
app.enableCors({
origin: 'http://localhost:5173',
});
编写update操作(使用useMutation)
编写对应的gql语句,定义了一个 GraphQL 变更(Mutation)查询,使用了 Apollo Client 提供的 gql 模板字符串。
php
export const UPDATE = gql`
mutation update($id: String!, $params: UserInput!){
update(id: $id, params: $params)
}
`;
```export const UPDATE = gql...`````: 这行代码定义了一个 GraphQL 变更操作,命名为 UPDATE。gql 函数用于将 GraphQL 查询字符串转换为 GraphQL AST(Abstract Syntax Tree),以便 Apollo Client 可以理解和发送到服务器。
mutation update($id: String!, $params: UserInput!)
: 这部分定义了一个 GraphQL 变更操作,命名为 update。它接受两个参数:$id
(一个字符串)和 $params
(一个类型为 UserInput 的输入对象)。这些参数是在调用这个变更操作时必须提供的, <math xmlns="http://www.w3.org/1998/Math/MathML"> i d 表示要更新的用户的唯一标识,而 id 表示要更新的用户的唯一标识,而 </math>id表示要更新的用户的唯一标识,而params 包含了更新用户时所需的各种属性(例如 name、email 等)。
update(id: $id, params: $params):
在变更操作的主体部分。
id: $id
表示使用传入的 $id 参数作为用户的唯一标识,
params: $params
表示使用传入的 $params 参数作为要更新的用户的属性。
<math xmlns="http://www.w3.org/1998/Math/MathML"> i d 和 id 和 </math>id和params是通过 Mutation 操作的参数传递给后端的实际值 。 <math xmlns="http://www.w3.org/1998/Math/MathML"> i d 对应了前面定义的 id 对应了前面定义的 </math>id对应了前面定义的id 输入参数, <math xmlns="http://www.w3.org/1998/Math/MathML"> p a r a m s 对应了 params 对应了 </math>params对应了params 输入参数。
这里的 update 是一个 GraphQL 变更(Mutation)操作的名称。在 GraphQL 中,update 是一个被服务器端实现的 Mutation 操作,用于执行数据的更新。
在前端应用程序中使用 Apollo Client 的 useMutation hook 方法时,需要提供一个包含相同变更操作名称(比如 update)的 Mutation 查询。这样,Apollo Client 就知道在发送请求时要将数据传递给服务器上名为 update 的变更操作。
在代码中,UPDATE 是一个 GraphQL 查询,它定义了一个名为 update 的 Mutation 操作。当你在前端应用程序中调用 useMutation hook时,你将使用这个 UPDATE 查询。例如,使用 useMutation hook 的方式可能如下:
这样定义了一个 GraphQL 变更查询后,可以在前端应用程序中使用 Apollo Client 的 useMutation hook 来执行这个变更操作,将更新的数据发送给服务器。这个查询使得前端应用程序能够与服务器进行双向数据交互,实现了数据的更新功能。
调用useMutation,返回update函数
sql
import { FIND, UPDATE } from './graphql/demo';
const [update] = useMutation(UPDATE);
const [update] = useMutation(UPDATE);
: 这行代码使用了useMutation hook,它是Apollo Client提供的一个React hook,用于执行GraphQL变更操作。在这里,useMutation hook接受了UPDATE变更操作作为参数,并返回一个数组,其中包含了一个函数(在这里命名为update)和其他一些属性。
update
: 这是一个函数,用于触发GraphQL变更操作 。在这个例子中,它被赋值给[update]的左侧,表示我们只关心返回的第一个函数。当调用update函数时,它将发送UPDATE变更操作的请求到GraphQL服务器。你可以通过传递变更操作所需的参数来执行相应的数据更新。
总的来说,这段代码的作用是使用useMutation hook,将从'./graphql/demo'导入的UPDATE变更操作绑定到一个函数update上。这个函数可以在组件中被调用,用于触发GraphQL服务器上的相应数据更新操作。
编写按钮的事件监听函数,参数可以从Graph调试面板中复制,
php
const onClickHandler = () => {
update({
variables: {
id: '22820297-e288-42ba-aadf-3a4062c5c3cb',
params: {
desc,
name,
},
},
});
};
update({ variables: { id: '22820297-e288-42ba-aadf-3a4062c5c3cb', params: { desc, name, }, }, })
;: 在onClickHandler函数中,update函数被调用,触发了GraphQL变更操作。这个操作的目的通常是将某个对象的属性更新为特定的值。
variables: { id: '22820297-e288-42ba-aadf-3a4062c5c3cb', params: { desc, name, }, },
: 这是一个包含变更操作所需参数的对象。id参数是一个字符串,表示要更新的对象的唯一标识符。params参数是一个对象,包含了两个属性desc和name,它们的值通常来自于组件中的状态或者用户的输入。
update函数是之前使用useMutation hook从UPDATE变更操作中获得的。通过调用update函数并传入包含了所需参数的对象,GraphQL客户端将向服务器发起一个GraphQL变更请求,执行相应的操作。
最终效果如下:
执行后具体的网络请求信息