HiTTO プロダクトチームブログ

「HiTTO(ヒット)」は、シゴトのナレッジを体系化し、新しいコミュニケーションを創り出す社内向けAIチャットボットです。

コーディング規約について(フロントエンド編)

早いもので今年も残り一週間ですね。 最近の寒さに震えるなかむーです。

今回はコーディング規約について触れてみようと思います。

HiTTOではHRTの精神のもと、基本的には実装者の設計方針やロジックを尊重していますが ある程度の方向性は揃えたい為lintに縛られない緩めのコーディング規約をドキュメント化し運用していました。

現在はlintで縛ってしまったものもあるのですが考え方等も含めて紹介させていただきます。

TypeScript

default exportではなくnamed exportを使用する

TypeScript的には有害との事なので。。named exportを使うようにしています。
詳細は以下の記事をご参照ください!

typescript-jp.gitbook.io

interface ではなく typeを使用する

interfaceだと定義されたプロパティ以外にも存在を許容するのでtypeで厳密に型定義を行っています。

importは相対パスでもOKだが上には辿らない

絶対パスだと分かりやすいので基本的には絶対パスでの指定に統一したいが、 直下のファイルにアクセスするのにも絶対パスだと少し使いづらいので 下の階層のファイルのみ相対パスでの参照を可能にしています。

コンポーネント共通の型はmodelsに定義する

複数のコンポーネントで共通で使用するような型はmodelsというディレクトリを用意してそちらの中に定義を書くようにしています。 例えばuserの権限の型だと

export const AccountRole = {
  admin: 'admin',
  user: 'user'
} as const;
export type AccountRole = typeof AccountRole[keyof typeof AccountRole];

のような定義と、GraphQLのenum⇔コンポーネントで使用する型 の変換も合わせて定義して使っています。(後述するGraphQLの型変換で使用)

  static fromGql(x: GqlAccountRole): AccountRole {
    switch (x) {
      case GqlAccountRole.ADMIN:
        return AccountRole.admin;
      case GqlAccountRole.USER:
        return AccountRole.user;
      default:
        throw new Error(`invalid role. ${x}`);
    }
  }

  static toGql(x: AccountRole): GqlAccountRole {
    switch (x) {
      case AccountRole.admin:
        return GqlAccountRole.ADMIN;
      case AccountRole.user:
        return GqlAccountRole.USER;
      default:
        throw new Error(`invalid role. ${x}`);
    }
  }

React

Templates以下のコンポーネントでGraphQLの型を使用しない

GraphQLと疎結合にするため、AtomicDesignで言うところのTemplates以下のコンポーネントではGraphQLの型定義は使用しないようにしています。
主にenumの為ですがPagesの部分でコンポーネントで使用する型とGraphQLの型を相互に変換しています。

参考:HiTTOを支える技術について (フロントエンド編) - HiTTO プロダクトチームブログ

必要に応じてContainerコンポーネントとPresentationalコンポーネントで分けて書く

シンプルなコンポーネントだと必要ないかもしれませんが、複雑なコンポーネントだとロジックの部分とPresentationalな部分が混在して見づらくなってしまい、保守性が下がってしまいます。
コンポーネントの規模に応じて必要であればロジックと見た目を分離して書くようにしています。

CSS

サイズの単位はpxを使う

HiTTOでは当初margin,padding,font-sizeの指定はremで行っていました。
しかし、Figmaのデザインとpx単位で合わせようとするとremでの表現が面倒なのと、どうしてもデザインとのずれが発生してしまうためすべてpxで指定するように変更しました。

styled-componentsに依存しすぎない

styleはstyled-componentsを使用して当てています。propsを使ってstyleの切り替え等を行っているとstyled-componentsへの依存が強くなってしまい、styled-componentsから脱却しようとした時に捨てるに捨てられない未来が来るかもしれないので、極力CSSに近い形で書いておく事で移行のハードルを下げようという方針です。

例えば下記のようなpropsを使った実装を

const Button = styled.a`
  display: inline-block
  ${props => props.primary && css`
    background: white;
    color: black;
  `}
`;

props使わないように実装するようにしています。

const Button = styled.a`
  display: inline-block
  &.primary {
    background: white;
    color: black;
  }
`;

最後に

他にもいくつかありますが主なルールを紹介させていただきました!

HiTTOでは採用のフローとして複業からのジョインを推奨しています。
自分に合わなかったらどうしよう。今の会社は辞めたくないけど気になる。。という方もマッチするかどうか複業で確認できるかと思いますので、ぜひご応募お待ちしております!

offers.jp

offers.jp

offers.jp

jobs.forkwell.com