🐛

【Vue.js】Vue3でmixinの代わりにComposition API functionsを使う

2021/12/11に公開

この記事はジャンルなしオンラインもくもく会 Advent Calendar 2021の11日目の記事です。ジャンルなしということなので、とりあえず最近少し触り始めたVue3について書いてみます。

概要

Vueにはロジックを再利用するmixinという機能が、用意されています。mixinの仕組みはVue3においても使用できますが、こちらのドキュメントに記載の通りあまり推奨されておらず、Composition APIを使うような案内がされています。mixinについて、けっこう手軽に使えるのは良いところではあると思いますが、俺がやらかしたVue mixinのアンチパターンから学ぶmixinの使い方と代替案にあるようなデメリットもあり、Vue3ではあまり積極的な使用は控えた方が良い、という方針になったのかなと考えられます。
では、Composition APIを使えと言われてもどう書けば良いのか、ということで今回は私的にこんな風に書けば良いのではというのをまとめてみます。

対応

参考にしてみた記事はCustom Composable Methods with Vue 3です。記事中のExample - API Requestsの項にある通り、useDadJokeのようなfunctionの形式で、使用したい変数や関数を定義していきます。
使用する側では、このuse関数から必要なものだけを取得していきます。

実装サンプル

Composition API functionsに関数だけ定義して返すような実装を、サンプルとしてのせておきます。

以下が関数の定義です。localStorageに保存してあるtokenをAPIで検証し、問題なければレスポンスのユーザ情報を返す関数を定義しています。

<script>
export default function useAuthFunction() {
  //トークンからユーザ情報を取得
  async function getUserFromToken(localStorage) {
    const $config = useRuntimeConfig();
    const token = localStorage.getItem("authToken");
    if (!token) {
      return undefined;
    }
    // APIでのtokenの検証
    try {
      const url = $config.API_HOST + "/user/loginCheckByToken";
      const params = {
        method: "POST",
        headers: {
          Authorization: token,
        },
      };
      // レスポンスにはユーザ情報が入る想定
      const res = await fetch(url, params);
      if (res.ok) {
        return await res.json();
      }
    } catch (_) {
      return undefined;
    }
    return undefined;
  }

  return {
    getUserFromToken,
  };
}
</script>

以下がこの関数を使う側です。上記でreturnしているgetUserFromTokenを使用します。

<script>
import useAuthFunction from "../customFunction/AuthFunctionComponent";

export default defineComponent({
  async setup() {
    const state = reactive({
      user: undefined,
    });
    const { getUserFromToken } = useAuthFunction();
    if (process.client) {
      state.user = await getUserFromToken(window.localStorage);
    }
    return { state };
  },
});
</script>

Discussion