概述
让我们将我们的列表数据与来自过去客人的评论相结合。使用GraphOS,这非常简单:只需点击几下即可!
在本课中,我们将
- 添加一个新的 子图 到我们的 超级图 中,使用 Studio
- 检查一个 操作 的 查询计划
介绍评论
我们即将了解评论 API;它是一个功能齐全的 GraphQL 服务器,具有模式、数据源 和数据提取器。
该reviews
服务收集并提供客人的反馈。我们可以 查询 它以获取其数据库中的所有评论,或提交新的评论。
让我们将这个 子图 和全新的功能集成到我们的 GraphQL API 中——我们可以通过克隆存储库并立即报告其模式来实现。无需任何调整!
克隆 reviews
在您的终端中,导航到 listings
目录之外,以便您位于主 dgs-federation
项目文件夹中。然后,运行以下命令来克隆 reviews
子图。
git clone https://github.com/apollographql-education/odyssey-federation-dgs-reviews.git reviews
注意: 我们在上面的命令中添加了 reviews
标志。这将在名为 reviews
的文件夹中克隆提供的存储库,以确保清晰度。
现在我们的项目结构如下
📦 dgs-federation┣ 📂 listings┣ 📂 reviews┗ 📂 router
让我们在新的 IDE 窗口中打开 reviews
并启动它。如果您使用的是 IntelliJ,请找到绿色的播放按钮,或在存储库终端中运行以下命令。
./gradlew bootRun
添加子图
让我们将我们的 reviews
模式发布到注册中心。
复制下面的命令,用 您 的值替换 APOLLO_GRAPH_REF
。然后,在打开到 reviews
目录的终端中,粘贴并运行它。
rover subgraph publish <APOLLO_GRAPH_REF> \--name reviews \--schema ./src/main/resources/schema/schema.graphqls \--routing-url https://127.0.0.1:8090/graphql
注意: listings
子图 在本地运行在端口 8080
上,而 reviews
子图 运行在 8090
上。确保在发布 reviews
模式时,您引用了正确的端口号!
现在,让我们返回 Studio,并导航到左侧菜单中的 子图 选项卡。我们会看到我们新的 reviews
子图 已经报告了——我们的 超级图 也增长了!
我们新的超级图模式
接下来,让我们通过导航菜单查看 变更日志,以了解 reviews
子图 向 API 添加了哪些新功能和功能。
我们可以看到我们的 图 已经增长——包含关于评论的所有类型和 字段!我们有两个新的 对象类型:Review
和 SubmitReviewResponse
。我们还有 ReviewInput
作为新的输入类型。并且我们有两个新的根 字段:Query.allReviews
和 Mutation.submitReview
。
所有这些新的类型和 字段 应该都来自 reviews
子图。我们可以通过前往 模式 页面来确认哪些 字段 来自哪个子图。
在 参考 选项卡下,选择 查询,我们可以看到进入我们 超级图 的入口点。 子图 列指示每个 字段 来自哪个 子图!
在这里,我们会看到 reviews
子图 贡献的新 字段:allReviews
。
我们还可以在 对象 下查看添加到我们模式中的新 对象类型。
我们的 超级图 已正式增长!
发送查询
评论和列表的数据触手可及;您是否迫不及待地想测试我们 超级图 的强大功能?让我们尝试发送一个涉及两个 子图 的 查询。
让我们回到 模式 页面中的 查询 选项卡,在那里我们可以看到进入我们 超级图 的所有可用入口点。在 模式 页面中的 操作 列中,单击 allReviews
旁边的播放图标。
这将打开 Explorer,并显示文档选项卡,其中包含 字段 以及我们可以用来构建 查询 的内容。
注意: 如果您在 操作 面板中当前有一个 操作,请清除它或打开新的 Explorer 选项卡。我们想要从这里开始!
在 allReviews
下,我们可以看到它的描述——"数据库中的所有评论列表"——以及每个返回的 Review
类型上可用于 查询 的 字段。让我们添加所有字段:id
、text
和 rating
。
query GetAllReviews {allReviews {idtextrating}}
这些数据来自 reviews
子图!现在让我们从 listings
子图 中引入数据:为什么我们不提取特定房源的数据呢?
在 Explorer 中有一个方便的快捷方式,可以搜索我们的模式以查找该 字段。按下 Command + K
或 Ctrl + K
访问聚光灯搜索。开始键入 listing
,则 Query.listing
字段 应该会弹出。
让我们添加 listing
字段 并请求其 title
。
最后,我们将重命名 操作 以使其更明确。将其命名为 GetAllReviewsAndListing
。
您的 查询 现在应该看起来像这样:
query GetAllReviewsAndListing($listingId: ID!) {allReviews {idtextrating}listing(id: $listingId) {title}}
以及在 Variables 部分:
{"listingId": "listing-1"}
让我们运行它!
哇哦,我们得到了数据!一个查询,但数据来自两个独立的子图 🤯🎉
查询计划
我们可以通过检查 查询计划 来验证每个 字段 的数据的确切来源。 查询计划 就像 操作 的蓝图: 路由器 用于将较小的操作发送到负责这些特定 字段 的 子图 的一组指令。
点击 Response 面板中的下拉菜单,选择 Query Plan。
我们可以将 查询计划 视为图表,或者如果我们选择 "Show plan as text" 图标,则可以将其视为文本。我们不必过分担心 查询计划 的语法—— 路由器 知道发生了什么!但这在我们开始使用更多 子图 和更复杂的查询(需要优化)时非常有用。
对于这个特定的 查询,我们可以看到 "Parallel" 这个词,表示 路由器 可以同时发出两个独立的请求:一个到 reviews
,另一个到 listings
。这些请求可以并行运行,因为 listings
和 reviews
都不依赖于对方的响应来解析自己的数据。
我们还可以看到 allReviews
字段 及其子字段来自 reviews
子图 (即 Fetch(service: "reviews")
部分),而 listing
字段 及其子字段来自 listings
子图。这两个较小的 操作 并行运行并由其自己的子图解析,而 路由器 负责将数据捆绑起来,以单个响应的形式返回给客户端。
添加 子图 相当简单!但是您可能感觉这两个子图中的数据仍然是独立的和孤立的。没有直接 连接 房源和评论,反之亦然。
新功能:房源的评分和评论
我们希望能够 查询 关于特定房源的详细信息:标题、描述、床位数量和便利设施,以及对其的评论!让我们更进一步——也包含房源的 overallRating
,它是根据所有评分计算得出的。
理想的 查询 看起来像这样:
query GetListingAndReviews {listing(id: "listing-1") {titledescriptionnumOfBedsamenities {namecategory}overallRatingreviews {idtext}}}
注意:为了便于在课程中进行参考,我们在 查询 中内联包含了房源的 id
。实际上,这个 id
参数 会被提取到 变量 中。
让我们深入研究我们的 reviews
数据,看看如何构建这个功能,并实现我们理想的 查询。
数据在 reviews
中
当我们启动 reviews
服务器时,它会自动在其内存数据库中播种一些示例评论。
reviews 表定义了四列: id
、 text
、 rating
和 listingId
。下表说明了这些数据的组合。
id | text | rating | listingId |
---|---|---|---|
1 | "哇,真是太棒的体验了!我以前从未住过洞穴,所以有点没准备。幸运的是,这个房源拥有我需要的安全保障和一切设施,让我可以应对任何情况。" | 4 | "listing-1" |
2 | "100% 享受荒野体验。如果您不是冒险家或户外爱好者,请不要预订。" | 5 | "listing-2" |
3 | "嘛,说真的,可以更好。我期待更多。湖是唯一的亮点。" | 2 | "listing-3" |
那个 listingId
字段 正是我们需要用来将特定评论与它所写的房源相关联的东西。
只有一个问题:除了我们数据库中的这一列之外,我们 reviews
子图 并不知道 什么 是 "房源"。同样,我们的 listings
子图 也不了解 reviews
!即使它们是同一个 超图 的一部分,每个 子图 都是独立存在的。
我们需要一种方法来连接这两个 子图 之间的数据,以实现我们梦寐以求的 查询 功能(提示:它被称为实体!)。这将涉及对两个子图进行一些更改,因此我们将首先设置正确的 超级图 开发环境。这将确保我们对一个子图所做的任何更改不仅按预期工作,而且还与另一个子图完美配合。
练习
主要收获
- 要添加新的 子图,我们可以使用 Studio UI 或 Rover CLI。
- 我们可以使用 Explorer 查看 路由器 的 查询计划。
下一步
在下一课中,让我们为本地开发做好准备。
分享您关于本课的问题和意见
本课程目前处于
您需要一个 GitHub 帐户才能在下面发帖。没有? 请改为在我们的 Odyssey 论坛上发帖。