top of page
  • nakaji

[React/gatsby/tailwind] テーブル要素のComponent化をして1行でテーブル追加できるようにリファクタリング

やりたいこと

現在、gatsby.jsで会社のホームページを作っており、以下のような表を色んなページで作成するという要件があります。

いわゆるヘッダなしテーブルです。テーブルの各行が(属性, 値)のペアーになっているような構造です。まずこれを愚直に記述すると以下のようなコードになります。

※CSSフレームワークは tailwindを使用しています。

<table class="rounded-t-lg m-5 w-5/6 mx-auto800 w-full border">
        <tr class="border-b">
          <td class="px-4 py-3 bg-secondary text-primary font-bold">会社名</td>
          <td class="px-4 py-3 bg-white text-black">XX会社</td>
        </tr>
        <tr class="border-b">
          <td class="px-4 py-3 bg-secondary text-primary font-bold">本社所在地</td>
          <td class="px-4 py-3 bg-white text-black">XXX-XXXX-XXXX</td>
        </tr>
        <tr class="border-b">
          <td class="px-4 py-3 bg-secondary text-primary font-bold">連絡先</td>
          <td class="px-4 py-3 bg-white text-black">XXX-XXXX-XXXX</td>
        </tr>
      </table>

いかがでしょうか?3行のテーブルですが、文字数がけっこう多くて読むのが大変ではないでしょうか。実際に色々なページにテーブルを追加することを想像すると、このコードをコピペ→値の部分だけ修正、という作業を想像するとなかなか大変そうですよね。また、途中でテーブルのデザインを変えたい時にも、それぞれの箇所に編集が必要となります。こういう作業に時間を費やすのは本質的では無く、要約すると拡張性・保守性の観点でも危うい実装と言えます。

ということでコードベースがスパゲッティ化する前に、今回はこのテーブルをリファクタリングし部品化することを目指します。

方針

今回のリファクタリングの方針は以下のような使い方が出来るように直したいかと思います。

  • テーブルを追加する際は、各行の(属性, 値)のセットだけをコードに書けば良い。

  • テーブルのスタイル(枠線の色、背景色など)は1つの箇所に設定箇所をまとめる。

リファクタリング

直していく過程

Step1:まずはそのままComponentにしてみる

まずはテーブルのDOMをそのままComponent化してみて、無事表示されることを確認。

import React from "react"
import '../utils/global.css'

const PairTable = () => (
    <table class="rounded-t-lg m-5 w-5/6 mx-auto800 w-full border">
        <tr class="border-b">
            <td class="px-4 py-3 bg-secondary text-primary font-bold">会社名</td>
            <td class="px-4 py-3 bg-white text-black">XX会社</td>
        </tr>
        <tr class="border-b">
            <td class="px-4 py-3 bg-secondary text-primary font-bold">本社所在地</td>
            <td class="px-4 py-3 bg-white text-black">XXX-XXXX-XXXX</td>
        </tr>
        <tr class="border-b">
            <td class="px-4 py-3 bg-secondary text-primary font-bold">連絡先</td>
            <td class="px-4 py-3 bg-white text-black">XXX-XXXX-XXXX</td>
        </tr>
    </table>
);

export default PairTable;
import PairTable from "../components/table"
...
<PairTable />
...

page1.js はだいぶシンプルになりました。しかしこのままだと、全く同じ内容のテーブルを表示することしか出来ずまだ実用レベルではありません。


Step2:テーブルの各セルの内容を動的に(完成版)

こちらを参考に、入力された変数から動的にテーブルの各行を生成し、生成した各行のDOMをテーブル<table>タグの適切な位置に挿入する、という実装に変更いたしました。

import React from "react"
import '../utils/global.css'

const PairTable = ({ values }) => {
    const rows = values.map((item) =>
        <tr class="border-b">
            <td class="px-4 py-3 bg-secondary text-primary font-bold">{item[0]}</td>
            <td class="px-4 py-3 bg-white text-black">{item[1]}</td>
        </tr>
    );

    return (
        <table class="rounded-t-lg m-5 w-5/6 mx-auto800 w-full border">
            {rows}
        </table>
    )
}

export default PairTable;

利用する側は以下のように、当初のリファクタリング方針であった各行の(属性, 値)のセットだけをコードに書けば良いです

import PairTable from "../components/table"
...
<PairTable values = {[['Key1','Value1'],['Key2','Value2']]}/>
...

ということで大分スッキリしましたね!

まずはこの部品をプロトタイプとして使っていきたいと思います。Reactやっている方はぜひご参考に。

bottom of page