88
64

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

React.Fragment の活用タイミング

Last updated at Posted at 2018-09-23

はじめに

本記事はReact.Fragmentの使い方に関して記載します。
恥ずかしながら、筆者はReact開発をはじめて数ヶ月後に、React.Fragmentの存在を知りました。。涙
このテクニックをご存知でない方向けに記事を書きました。

問題点

Reactにて複数のエレメントをrender()関数にて返す必要がある場合、1つのタグにまとめる必要があります。

class Table extends React.Component {
  render() {
    return (
      <table>
        <tr>
          <Columns column1="col1" column2="col2" />
        </tr>
      </table>
    );
  }
}

class Columns extends React.Component {
  render() {
    const { column1, column2 } = this.props;
    // Error!!!
    return (
      <td>{column1}</td>
      <td>{column2}</td>
    );
  }
}

ReactDOM.render(<Table />, document.getElementById("root"));

このとき、下記エラーが発生します。

index.js: Adjacent JSX elements must be wrapped in an enclosing tag

Columnsクラスにて2つのタグを返そうとしていますが、これはReactではNGです。

    // NG case. 1つのタグにまとめる必要あり
    return (
      <td>{column1}</td>
      <td>{column2}</td>
    );

しばらくは私は

タグを追加して、エラーを回避していました (!!これは間違い)
  return (
    <div>
      <td>{column1}</td>
      <td>{column2}</td>
    </div>
  );

divタグを追加するとエラーは解消しますが、無駄なタグがふくまれてしまいます。

<table>
  <tr>
    <div> <!-- このdivは不要 -->
      <td>col1</td>
      <td>col2</td>
    </div>
  </tr>
</table>

解決策

ReactにはReact.Fragmentタグが存在しており、このタグを追加することで、エラーは回避可能で、かつ無駄なタグが含まれることもなくなります。

class Columns extends React.Component {
  render() {
    const { column1, column2 } = this.props;
    return (
      <React.Fragment>
        <td>{column1}</td>
        <td>{column2}</td>
      </React.Fragment>
    );
  }
}

生成されるHTMLは下記になります。無駄なタグは生成されません。

<table>
  <tr>
    <td>col1</td>
    <td>col2</td>
  </tr>
</table>

サンプルコードはこちら
https://codepen.io/japanese-engineer/pen/yxrQNv

補足

  • ツールによっては short syntax (<>>) の指定も可能です。ただ、多くのツールではshort syntax はサポートされてないので注意が必要です。

  • React.Fragmentはkeyを指定可能です。必要に応じてkeyを追加する必要があります。
    下記例ではReact.Fragmentを配列として返しています。この場合、keyを追加しないと、Reactは警告を出します

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

まとめ

React にて複数の子エレメントを返す場合、React.Fragmentタグを使うことで、無駄なタグを省くことができます。

参照 https://reactjs.org/docs/fragments.html

88
64
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
88
64

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?