maesblog

React v16.2.0: Fragments機能の改善【日本語翻訳】

現在2018年3月ですが、そろそろReact v16.3がリリースされると言われています。React v16.3の目玉機能はcontext APIと言われています。そんな中、私は最近はAngularばかり書いていて、Reactの最新情報をあまり追えていません。React v16.3がリリースされる前に、React v16.2を押さえておこうと思って、今更ですがReact v16.2のリリース内容についてのReactの公式ブログの記事を翻訳してみました。React v16.2の目玉機能は何と言ってもFragmentsです。Reactの書き方を大きく改善してくれる機能です。ぜひ参考にしてみてください。

React_v16_2_0 fragments
React v16.2.0: Improved Support for Fragments

November 28, 2017 by Clement Hoang

React 16.2 is now available! The biggest addition is improved support for returning multiple children from a component’s render method. We call this feature fragments:

React 16.2がついに利用できるようになりました。今回のバージョンでは、コンポーネントのrenderメソッドから複数のchildrenを返す機能を大きく改善しました。この機能は、fragmentsと言います。

Fragments look like empty JSX tags. They let you group a list of children without adding extra nodes to the DOM:

fragmentsは以下のような空のJSXのタグです。DOMに余計なnodeを追加せずに複数のchildrenをグループ化することができます。

render() {
  return (
    <>
      <ChildA />
      <ChildB />
      <ChildC />
    </>
  );
}

This exciting new feature is made possible by additions to both React and JSX.

この刺激的な新しい機能はReactとJSXの両方に追加することによって利用可能となります。

What Are Fragments? – Fragmentsとは?

A common pattern is for a component to return a list of children. Take this example HTML:

コンポーネントから複数のchildrenを返す一般的な方法としては、以下のようなHTMLの例になるでしょう。

Some text.
<h2>A heading</h2>
More text.
<h2>Another heading</h2>
Even more text.

Prior to version 16, the only way to achieve this in React was by wrapping the children in an extra element, usually a div or span:

React 16以前のバージョンでは、これを実現する唯一の方法として、余計な要素(一般的にdivspan)でchildrenをラップする必要がありました。

render() {
  return (
    // Extraneous div element :(
    <div>
      Some text.
      <h2>A heading</h2>
      More text.
      <h2>Another heading</h2>
      Even more text.
    </div>
  );
}

To address this limitation, React 16.0 added support for returning an array of elements from a component’s render method. Instead of wrapping the children in a DOM element, you can put them into an array:

この制約に対処するべく、React 16.0ではコンポーネントのrenderメソッドから要素の配列を返すことをサポートしました。DOM要素でchildrenをラップする代わりに、それらを配列の中に格納すればよくなりました。

render() {
 return [
  "Some text.",
  <h2 key="heading-1">A heading</h2>,
  "More text.",
  <h2 key="heading-2">Another heading</h2>,
  "Even more text."
 ];
}

However, this has some confusing differences from normal JSX:

しかし、この方法は標準的なJSXとは異なるため混乱を招く可能性があります。

・Children in an array must be separated by commas.
・Children in an array must have a key to prevent React’s key warning.
・Strings must be wrapped in quotes.

  • 配列内のchildrenはカンマによって区切られていなくてはいけない
  • 配列内のchildrenはReactの警告(key warning)を出さないようにkey属性をつけなくてはいけない
  • 文字列はダブルクォーテーションなどの引用符でラップされていなければいけない

To provide a more consistent authoring experience for fragments, React now provides a first-class Fragment component that can be used in place of arrays.

fragmentsのより一貫性のあるオーサリングエクスペリエンスを提供するために、Reactは配列の代わりとなるファーストクラス(第一級)コンポーネントとしてFragmentコンポーネントを提供するようにしました。

render() {
  return (
    <Fragment>
      Some text.
      <h2>A heading</h2>
      More text.
      <h2>Another heading</h2>
      Even more text.
    </Fragment>
  );
}

You can use <Fragment /> the same way you’d use any other element, without changing the way you write JSX. No commas, no keys, no quotes.

これまで通りJSXの書き方を変えることなく、<Fragment />を他の要素と同じように使えるようになります。カンマも、key属性も、クォーテーションも必要ありません。

The Fragment component is available on the main React object:

FragmentコンポーネントはReactオブジェクトで利用することができます。

const Fragment = React.Fragment;

<Fragment>
  <ChildA />
  <ChildB />
  <ChildC />
</Fragment>

// This also works
<React.Fragment>
  <ChildA />
  <ChildB />
  <ChildC />
</React.Fragment>

JSX Fragment Syntax – JSXのFragment構文

Fragments are a common pattern in our codebases at Facebook. We anticipate they’ll be widely adopted by other teams, too. To make the authoring experience as convenient as possible, we’re adding syntactical support for fragments to JSX:

fragmentsはFacebookのコードベースでは一般的なパターンとなっています。おそらく他のチームにも広く採用されていくでしょう。できる限りオーサリングエクスペリエンスが便利となるように、fragmentsの構文サポートをJSXに追加していく予定です。

render() {
  return (
    <>
      Some text.
      <h2>A heading</h2>
      More text.
      <h2>Another heading</h2>
      Even more text.
    </>
  );
}

In React, this desugars to a <React.Fragment/> element, as in the example from the previous section. (Non-React frameworks that use JSX may compile to something different.)

上記のセクションの例のように、これはReactにおける<React.Fragment/>要素に限定されます。(JSXに対応する非Reactのフレームワークでは、異なったものとしてコンパイルされるかもしれません。)

Fragment syntax in JSX was inspired by prior art such as the XMLList() <></> constructor in E4X. Using a pair of empty tags is meant to represent the idea it won’t add an actual element to the DOM.

JSXのFragment構文は、E4XXMLList() <></>コンストラクタのような先行技術からインスパイヤされたものとなります。ペアの空タグを使うことは、実際の要素をDOMに追加しないと言うアイデアの現れを意味しています。

Keyed Fragments

Note that the <></> syntax does not accept attributes, including keys.

<></>構文は、key属性を含めて、一切属性を受け入れないと言うことに注意してください。

If you need a keyed fragment, you can use <Fragment /> directly. A use case for this is mapping a collection to an array of fragments — for example, to create a description list:

もしkey属性を必要とする場合は、直接<Fragment />を使いましょう。このkey属性を必要とするユースケースとしては、例えば記述リストを作成するために、コレクションをfragmentsの配列にマッピングすることなどが挙げられます。

function Glossary(props) {
  return (
    <dl>
      {props.items.map(item => (
        // Without the `key`, React will fire a key warning
        <Fragment key={item.id}>
          <dt>{item.term}</dt>
          <dd>{item.description}</dd>
        </Fragment>
      ))}
    </dl>
  );
}

key is the only attribute that can be passed to Fragment. In the future, we may add support for additional attributes, such as event handlers.

key属性はFragmentに渡せる唯一の属性です。将来的には例えばイベントハンドラーのような属性のサポートを行うかもしれません。

Live Demo

You can experiment with JSX fragment syntax with this CodePen.

こちらのCodePenでJSXのfragments構文を試すことができます。

Support for Fragment Syntax – Fragment構文のサポート

Support for fragment syntax in JSX will vary depending on the tools you use to build your app. Please be patient as the JSX community works to adopt the new syntax. We’ve been working closely with maintainers of the most popular projects:

JSXにおけるfragment構文のサポートは、アプリをビルドするために使っているツールに大きく依存します。JSXのコミュニティが新しい構文を採用するように動いているので、辛抱強くお待ちください。最も有名なプロジェクトのメンテナーたちと緊密に協力しあってきています。

Create React App

Experimental support for fragment syntax will be added to Create React App within the next few days. A stable release may take a bit longer as we await adoption by upstream projects.

fragment構文の実験的なサポートは近日中にCreate React Appに追加される予定です。なお、アップストリームのプロジェクトによる採用を待つ必要があるので、安定板のリリースは多少時間がかかります。

Babel

Support for JSX fragments is available in Babel v7.0.0-beta.31 and above! If you are already on Babel 7, simply update to the latest Babel and plugin transform:

JSXのfragmentsはBabel v7.0.0-beta.31以上で利用可能です!文字、すでにBabel 7を利用している場合、babelとtransform系のプラグインを最新版に更新するだけで済みます。

# for yarn users
yarn upgrade @babel/core @babel/plugin-transform-react-jsx
# for npm users
npm update @babel/core @babel/plugin-transform-react-jsx

Or if you are using the react preset:

もしくはreactのpresetを使用している場合は以下の通りです。

# for yarn users
yarn upgrade @babel/core @babel/preset-react
# for npm users
npm update @babel/core @babel/preset-react

Note that Babel 7 is technically still in beta, but a stable release is coming soon.

Babel 7は技術的にまだベータ版ですが、まもなく安定板がリリースされる予定です

Unfortunately, support for Babel 6.x is not available, and there are currently no plans to backport.

残念ながら、Babel 6.xでは利用できませんし、現在のところバックポートへの対応の予定はありません。

Babel with Webpack (babel-loader)

If you are using Babel with Webpack, no additional steps are needed because babel-loader will use your peer-installed version of Babel.

もしBableをWebpackで使っている場合は、babel-loaderがpeerインストールされたBabelのバージョンを使用しているので、これ以上何もする必要はありません。

Babel with Other Frameworks

If you use JSX with a non-React framework like Inferno or Preact, there is a pragma option available in babel-plugin-transform-react-jsx that configures the Babel compiler to de-sugar the <></> syntax to a custom identifier.

もしJSXをInfernoやPreactのような非Reactフレームワークで使用している場合は、babel-plugin-transform-react-jsxで利用可能なプラグマオプションがあります。これは、<></>構文をカスタム識別子にde-sugarするためにBabelコンパイラを設定します。

TypeScript

TypeScript has full support for fragment syntax! Please upgrade to version 2.6.2. (Note that this is important even if you are already on version 2.6.1, since support was added as patch release in 2.6.2.)

TypeScriptはfragment構文を完全にサポートしています!バージョン2.6.2にアップグレードしてください。(サポートは2.6.2のリリースでパッチとして追加されたので、すでにバージョン2.6.1にしていたとしても、これ重要なことです。)

Upgrade to the latest TypeScript with the command:

以下のコマンドで最新版のTypeScriptにアップグレードできます。

# for yarn users
yarn upgrade typescript
# for npm users
npm update typescript

Flow

Flow support for JSX fragments is available starting in version 0.59! Simply run

Flowでは、バージョン0.59からJSXのfragmentsのサポートが開始されています!以下を実行するだけで、

# for yarn users
yarn upgrade flow-bin
# for npm users
npm update flow-bin

to update Flow to the latest version.

Flowは最新版にアップデートされます。

Prettier

Prettier added support for fragments in their 1.9 release.

Prettierは1.9のリリースでfragmentsのサポートが追加されました。

ESLint

JSX Fragments are supported by ESLint 3.x when it is used together with babel-eslint:

babel-eslintを使っていれば、JSXのfragmentsはESLint 3.xによってサポートされています。

# for yarn users
yarn add eslint@3.x babel-eslint@7
# for npm users
npm install eslint@3.x babel-eslint@7

or if you already have it, then upgrade:

すでにインストール済みであれば、以下でアップグレードします。

# for yarn users
yarn upgrade eslint@3.x babel-eslint@7
# for npm users
npm update eslint@3.x babel-eslint@7

Ensure you have the following line inside your .eslintrc:

.eslintrcの中に以下が含まれていることを確認してください。

"parser": "babel-eslint"

That’s it!

これで完了です!

Note that babel-eslint is not officially supported by ESLint. We’ll be looking into adding support for fragments to ESLint 4.x itself in the coming weeks (see issue #9662).

babel-eslintはESLintによって正式にサポートされていないことに注意してください。今後数週間でESLint 4.x自体にfragmentsのサポートを追加することを検討しています(詳細はissue #9662)。

Editor Support

It may take a while for fragment syntax to be supported in your text editor. Please be patient as the community works to adopt the latest changes. In the meantime, you may see errors or inconsistent highlighting if your editor does not yet support fragment syntax. Generally, these errors can be safely ignored.

お使いのエディターではfragment構文のサポートにもうしばらく時間がかかるかもしれません。コミュニティが最新の変更を採用するべく働きかけているので辛抱強くお待ちください。その間、もしお使いのエディターがfragment構文のサポートをしていなかった場合、エラーや意味のないハイライトなどが出るかもしれません。一般的にこれらのエラーは無視してもらって問題ありません。

TypeScript Editor Support

If you’re a TypeScript user — great news! Editor support for JSX fragments is already available in Visual Studio 2015, Visual Studio 2017, Visual Studio Code and Sublime Text via Package Control.

TypeScriptユーザーの方であれば朗報があります!Visual Studio 2015Visual Studio 2017Visual Studio CodePackage Controlを通してのSublime TextなどではすでにJSXのfragmentsを利用できるようになっています。

Other Tools

For other tools, please check with the corresponding documentation to check if there is support available. However, if you’re blocked by your tooling, you can always start with using the <Fragment> component and perform a codemod later to replace it with the shorthand syntax when the appropriate support is available.

他のツールについては、該当するドキュメントを参照して、利用可能であるかどうかを確認してみてください。ただし、ツールによりブロックされている場合は、<Fragment>コンポーネントを使用すればいつでも利用を開始することができます。そして適切なサポートがなされた際に、簡略構文に置き換えてください。

Installation – インストール 

React v16.2.0 is available on the npm registry.

React v16.2.0はnpmレジストリで利用可能です。

To install React 16 with Yarn, run:

yarnでインストールするには、以下を実行します。

yarn add react@^16.2.0 react-dom@^16.2.0

To install React 16 with npm, run:

npmでインストールするには、以下を実行します。

npm install --save react@^16.2.0 react-dom@^16.2.0

We also provide UMD builds of React via a CDN:

もちろんCDN経由でのReactのUMDビルド版も提供しています。

<script crossorigin src="https://unpkg.com/react@16/umd/react.production.min.js"></script>
<script crossorigin src="https://unpkg.com/react-dom@16/umd/react-dom.production.min.js"></script>

Refer to the documentation for detailed installation instructions.

インストールの手順についての詳細は、ドキュメントを参照してください。

Changelog – 変更ログ

React

・Add Fragment as named export to React. (@clemmy in #10783)
・Support experimental Call/Return types in React.Children utilities. (@MatteoVH in #11422)

  • Reactに名前付きのexportとしてFragmentを追加しました。(@clemmy in #10783
  • React.Childrenユーティリティに実験的なCall/Returnタイプをサポートしました。(@MatteoVH in #11422

React DOM

・Fix radio buttons not getting checked when using multiple lists of radios. (@landvibe in #11227)
・Fix radio buttons not receiving the onChange event in some cases. (@jquense in #11028)

  • 複数のradioボタンのリストを使っている際にチェックされないradioボタンのバグを修正しました。(@landvibe in #11227
  • いくつかのケースでonChangeイベントを受け取らないradioボタンのバグを修正しました。(@jquense in #11028

React Test Renderer

Fix setState() callback firing too early when called from componentWillMount. (@accordeiro in #11507)

componentWillMountから呼ばれた際に、setState()のコールバッグが早すぎるバグを修正しました。(@accordeiro in #11507

React Reconciler

Expose react-reconciler/reflection with utilities useful to custom renderers. (@rivenhk in #11683)

react-reconciler/reflectionにカスタムレンダラに役立つユーティリティを追加しました。(@rivenhk in #11683

Internal Changes

Many tests were rewritten against the public API. Big thanks to everyone who contributed!

パブリックなAPIに足してい多くのテストが書き換えられました。コントリビュートしてくれたみなさんに大変感謝しています!

Acknowledgments – 謝辞

This release was made possible by our open source contributors. A big thanks to everyone who filed issues, contributed to syntax discussions, reviewed pull requests, added support for JSX fragments in third party libraries, and more!

今回のリリースは多くのオープンソースコントリビュータたちによって可能となりました。イシューを上げ、構文のディスカッションに参加し、プルリクエストをレビューし、JSXのfragmentsのサポートをサードパーティのライブラリに追加などしてくれた全てのみなさんに大変感謝しています!

Special thanks to the TypeScript and Flow teams, as well as the Babel maintainers, who helped make tooling support for the new syntax go seamlessly.

新しい構文のサポートをシームレスにサポートしてくれたBabelのメンテナーだけでなく、TypeScriptFlowのチームに特別な感謝をいたします。

Thanks to Gajus Kuizinas and other contributors who prototyped the Fragment component in open source.

オープンソースでFragmentコンポーネントのプロトタイプの開発を行ってくれたGajus Kuizinasとその他のコントリビュータに感謝いたします。

まとめ

いかがでしたでしょうか。React v16.2のfragmentsは、コンポーネントごとに毎回余計なルート要素を用意する必要をなくしてくれるもので、結構使うケースは多いんじゃないかと思います。この機能は積極的に使えるものだと思います。記事内にあった注意点に気をつけて、利用してみてください。

コメント

  • 必須

コメント