リファクタリングチャレンジ　Web Speed Hackathon 2021 mini

# 初めに
[HCB Advent Calendar 2021](https://qiita.com/advent-calendar/2021/hcb-2021)
アドベントカレンダー23日目の記事になります。（大遅刻:26日）

テストコードやパフォーマンスチューニングができないWebフロントエンジニアの需要は少ないといわれたので、
必死こいて勉強する記事です。今回は、コードを読んで、処理に無駄がありそうなところや、操作性が悪くなっているところを発見し、修正する回にしようと思います。（スコアは見ません。）

ゆるく記事を書くので興味がある方は覗いてってください（メモ書きのような記事です）

勉強資料として
[Web Speed Hackathon 2021 mini](https://github.com/CyberAgentHack/web-speed-hackathon-2021)
を使います。

## 本題
### 条件分岐
./client/src/components/application/Navigation/Navigation.jsx
無駄な条件分岐があったので統一

```
{activeUser !== null ? (
  <NavigationItem
    icon={<FontAwesomeIcon iconType="edit" styleType="solid" />}
    onClick={onRequestOpenPostModal}
    text="投稿する"
    />
) : null}
{activeUser !== null ? (
  <NavigationItem
     href={`/users/${activeUser.username}`}
     icon={<FontAwesomeIcon iconType="user" styleType="solid" />}
     text="マイページ"
     />
) : null}
{activeUser === null ? (
  <NavigationItem
    icon={<FontAwesomeIcon iconType="sign-in-alt" styleType="solid" />}
    onClick={onRequestOpenAuthModal}
    text="サインイン"
    />
) : null}      
```

↓

```
{activeUser !== null ?
  (
    <>
      <NavigationItem
        icon={<FontAwesomeIcon iconType="edit" styleType="solid" />}
        onClick={onRequestOpenPostModal}
        text="投稿する"
        />
      <NavigationItem
        href={`/users/${activeUser.username}`}
        icon={<FontAwesomeIcon iconType="user" styleType="solid" />}
        text="マイページ"
        />
      </>
  )
  :
  <NavigationItem
  icon={<FontAwesomeIcon iconType="sign-in-alt" styleType="solid" />}
  onClick={onRequestOpenAuthModal}
  text="サインイン"
  />
}
```

### addEventListenerのpassiveオプション
addEventListenerのpassive設定をtrueにしてあげると、preventDefaultを読んでいないことをブラウザに伝達する。preventDefaultをしないと、eventListenerを実行するたびに、毎回設定された関数を再解釈し、すべて実行してしまう。そうなると、処理として記述されている2の18乗回の処理がスクロールするたびに実行されて、とても操作できない動作になる。（そもそも2の18乗とか絶対いらない...）

```
    const handler = () => {
      // 念の為 2の18乗 回、最下部かどうかを確認する
      const hasReached = Array.from(Array(2 ** 18), () => {
        return window.innerHeight + Math.ceil(window.scrollY) >= document.body.offsetHeight;
      }).every(Boolean);

      // 画面最下部にスクロールしたタイミングで、登録したハンドラを呼び出す
      if (hasReached && !prevReachedRef.current) {
        // アイテムがないときは追加で読み込まない
        if (latestItem !== undefined) {
          fetchMore();
        }
      }

      prevReachedRef.current = hasReached;
    };

    // 最初は実行されないので手動で呼び出す
    prevReachedRef.current = false;
    handler();

    document.addEventListener('wheel', handler, { passive: false });
    document.addEventListener('touchmove', handler, { passive: false });
    document.addEventListener('resize', handler, { passive: false });
    document.addEventListener('scroll', handler, { passive: false });
    return () => {
      document.removeEventListener('wheel', handler);
      document.removeEventListener('touchmove', handler);
      document.removeEventListener('resize', handler);
      document.removeEventListener('scroll', handler);
    };
```

```
```

### promise処理のつなげ方
promiseはメソッドチェーンを使って処理に成功した時と、失敗した時の処理をまとめてかける。

```
const promise = fetcher(apiPath);

promise.then((allData) => {
  setResult((cur) => ({
    ...cur,
    data: [...cur.data, ...allData.slice(offset, offset + LIMIT)],
    isLoading: false,
  }));
  internalRef.current = {
    isLoading: false,
    offset: offset + LIMIT,
  };
});

promise.catch((error) => {
  setResult((cur) => ({
    ...cur,
    error,
    isLoading: false,
  }));
  internalRef.current = {
    isLoading: false,
    offset,
  };
});
```

↓

```
fetcher(apiPath)
  .then((allData) => {
    setResult((cur) => ({
      ...cur,
      data: [...cur.data, ...allData.slice(offset, offset + LIMIT)],
      isLoading: false,
    }));
    internalRef.current = {
      isLoading: false,
      offset: offset + LIMIT,
    };
  })
  .catch((error) => {
    setResult((cur) => ({
      ...cur,
      error,
      isLoading: false,
    }));
    internalRef.current = {
      isLoading: false,
      offset,
    };
  });
```

## 最後に
今回まともに記事を書いてないうえに、大遅刻していますがここまでにしたいと思います。
Webパフォーマンスを学んでいく中で多くの学びがありました。今後も勉強・実践して力をつけていきます。