Relay Modern 介绍

Relay Modern 是新版本的 Relay ,从根本上设计成更易于使用,更可扩展,最重要的是能够提高移动设备的性能。 Relay Modern 通过静态查询和提前生成代码来实现。

入门#

升级到 react-relay v1.0.0 #

Relay v1.0 介绍了 Relay Modern API:

yarn add react-relay

当升级现有的 Relay 应用程序, 替换所有 require('react-relay')require('react-relay/classic') 就能继续的载入 Relay Classic API。

设置 babel-plugin-relay #

Relay Modern 需要一个 Babel 插件来转换 GraphQL 为运行时代码:

yarn add --dev babel-plugin-relay

添加 "relay" 到.babelrc文件的插件列表。 如果升级现有的 Relay 应用程序,请参阅文档

设置 relay 编译器 #

Relay Modern's 编译的前提是需要更新 Relay 编译器:

yarn add --dev relay-compiler

在 Relay 应用程序中对任何 GraphQL 进行更改后,请运行 Relay 编译器。 添加 yarn script是有帮助的。在你的package.json文件中添加一个条目到"scripts"

"relay": "relay-compiler --src ./src --schema path/schema.graphql"

然后在编辑您的应用程序文件后,只需运行yarn run relay生成新文件,或者 yarn run relay -- --watch 将编译器作为一个持续运行的进程,每当您保存时会自动生成新文件。

JavaScript 环境要求 #

The Relay Modern 在NPM上分发的现代软件包使用广泛支持的ES5版本的JavaScript来支持尽可能多的浏览器环境。

然而,Relay Modern 预计使用JavaScript的全局类型 (Map, Set, Promise, Object.assign) 来定义. 如果您支持旧版浏览器和可能尚未提供本机的设备,请考虑在捆绑的应用程序中包含全局聚合填充,例如core-jsbabel-polyfill

使用 core-js 来支持旧版浏览器的 Relay 的聚合环境可能如下:

require('core-js/es6/map');
require('core-js/es6/set');
require('core-js/es6/promise');
require('core-js/es6/object');

require('./myRelayApplication');

迁移到 Relay Modern #

迁移 一个典型的 Relay 应用程序到 Relay Modern 不需要从头开始重写。 相反,您可以一次将一个组件转换为 Relay Modern API ,同时继续使用可用的应用程序。所有组件都被转换后,可以使用越来越小的 Relay Modern 运行时。

在迁移过程中,使用 Relay 兼容 工具和API来处理 Relay Classic 和 Relay Modern.

Idea #

React 允许将视图定义为每个组件,每个组件负责呈现UI的一部分。组合其他的组件是建构复杂 UI 的方法。每一个 React 组件不需要知道被组装的 组件的内部运行机制。

Relay 组合 React 和 GraphQL,更进一步地实现了封装。它允许组件指定他们需要什么数据,而Relay框架提供数据。这使得内部组件的数据需求不透明,并允许组合这些需求。试想应用程序需要的数据被放到组件,应该让它更容易搞清楚什么字段需要,而什么字段不需要。

术语 #

容器 #

Relay Modern 将标准反应组件与其数据要求的描述相结合,表示为一个或多个GraphQL片段。 每个容器本身就是一个标准的React组件,可以使用标准的React API(例如 <YourComponent prop={...} />)来渲染。 渲染时,,容器将从 Relay 缓存读取其片段的数据。随着片段数据的更改 - 例如由于变更, Subscriptions或更新的查询响应 - 容器将自动重新渲染组件。

createFragmentContainer 返回一个基本容器,无法获取超出其片段中声明的附加数据。Relay Modern 还为动态用例提供了更先进的容器(以前在 Relay Classic 中通过处理 setVariables):

提取数据(以名 "See More") #

createRefetchContainer 是一个变体。 createFragmentContainer 解决了 "see more" 的用例。 其中数据的子集最先被渲染,然后根据需要提取附加的数据。起初提取容器的片段就像​片段容器一样为其片段提取数据,但也提供了一种可以获取附加数据的方法 refetch(),也可以使用不同的变量读取数据来重新渲染容器。

分页集合 #

这是通用提取容器的特化, 它是针对通过连续更多页面的数据和项目集合分页的常见场景而设计的。 查看 createPaginationContainer for details.

查询渲染 #

QueryRenderer 管理GraphQL查询的执行。它使用给定的变量发送查询,解析响应,将数据保存到内部缓存,最后渲染视图。

Relay 环境 #

Relay Environment 实例封装了GraphQL数据的内存缓存和提供对GraphQL服务器访问的网络层。 环境对象通常不被开发人员直接使用,而是传递给每个对象 QueryRenderer它们使用环境来访问,修改和获取数据。在容器内,可以通过访问当前的环境 执行 mutation.

网络层 #

创建 Relay 的实例时,应用程序必须提供 网络层。网络层是符合简单接口的对象,通过该接口, mutations和 Subscriptions。 本质上,这个对象告诉 Relay 如何跟 GraphQL 服务器通信。

工作流程 #

新API背后的一大优点是,可以通过提前执行工作,从应用程序的运行时间到构建时间,来实现更高效的执行。因此,对GraphQL片段的更改需要构建步骤来重新生成一组工件。更多关于 Relay 编译器

比较 Relay Classic 和 Relay Modern #

Relay Modern 可以实现多种新功能。有些可通过兼容 API获得,而其他则需要完全升级到Modern运行时。 查看 Relay Modern 新功能 的更多细节。