💨

hygenを導入する

2023/03/25に公開

hygenとは

プロジェクト内のファイルなどを自動生成するためのツールです。
hygenを使用することで、カスタマイズ可能なテンプレートを使って自動生成タスクを実行することができます。
ReactのコンポーネントファイルやStorybookのファイルを同時に自動生成することが可能です。
予めテンプレートを作成しておき、CLIでhygenを起動することで対話的にコードを生成することができるので、毎回同じコードを書く必要がなくなります。

公式ドキュメント:
https://www.hygen.io/

使い方:

1, インストール

$ npm install --save-dev hygen

2, 初期化

$ npx hygen init self

これを実行することでプロジェクトルートに_templatesディレクトリが生成されます。生成される_templatesディレクトリ内にはgeneratorとinitというフォルダがあり、この中にはサンプルコードが入っています。自動生成するファイルは_templates内に作っていきます。
テンプレートの一番最初に書かれているtoは、どこのディレクトリに配置するかを決定します。

コンポーネントのテンプレートファイル

Component.tsx.ejs.t
---
to: src/components/<%= path %>/<%= name %>.tsx
---
<% if (have_props) { -%>
export type <%= name %>Props = {};
<% } -%>
 
export const <%= name %>: <%- type_annotate %> = <%= props %> => {
  return <></>
}
コンポーネントのStorybook用ファイル
Component.stories.tsx.ejs.t
---
to: src/components/<%= path %>/<%= name %>.tsx
---
<% if (have_props) { -%>
export type <%= name %>Props = {};
<% } -%>
 
export const <%= name %>: <%- type_annotate %> = <%= props %> => {
  return <></>
}

次にコマンドライン上での捜査内容を記述するファイルを作ります。
これでどういった対話にするかを決めれる為、編集しましょう

index.js
module.exports = {
    prompt: ({inquirer, _args}) => {
        const questions = [
            {
                type: "select", // 対話の形式。inputは入力。selectの場合は選択肢を提示。
                name: "dir", // 入力された値を格納する変数の名前
                message: "どのディレクトリに作成しますか? ex: ato ms" // コマンドライン上で聞かれる質問
                choices: ["atoms", "molecules", "organisms", "templates", "pages"], // selectの場合に表示される選択肢
            },
            {
                type: "input",
                name: "name",
                message: "コンポーネント名は何ですか? ex: Button"
            },
            {
                type: "confirm",
                name: "have_props",
                message: "Propsは持ちますか?",
                choices: ["Yes", "No"],
                initial: "Yes"
            }
        ];
        return inquirer.prompt(questions).then((answers) => {
          const { dir, name, have_props } = answers;
         
          const { join } = require("node:path");
     
          const path = join(`${dir || "src/"}`, "/");
          const type_annotate = have_props ? `React.VFC<${name}Props>` : "React.VFC";
          const props = have_props ? "(props)" : "()";
          return { ...answers, path, type_annotate, props }; // テンプレート上で使用する変数
        });
    }
}

type: 開発者自身が入力するinputや選択型のselectなどがあります
name: inputやselectで入力した値が入る変数名となります
message: 入力する際のメッセージとなります

以下のコマンドで自動生成を実行します。

$ npx hygen fc new
✔ どのディレクトリに作成しますか? ex: atoms · atoms
✔ コンポーネント名は何ですか? ex: Button · RadioPropsは持ちますか? (Y/n) · true
 
Loaded templates: _templates
       added: src/stories/atoms/Radio/Radio.stories.tsx
       added: src/components/atoms/Radio/Radio.tsx
       added: app/hello.js

hygenを使うと今まで毎回同じ記述をしていた箇所をまるっと移譲することができます。特にReactでコンポーネントを作る際は、css modulesやtest、storybook用のファイルを同時に作成するケースがあると思いますが、hygenを使うとコマンド一つで一気に生成できちゃう。

Discussion