💨

一日一処: NuxtでAPIのMockを使用する時のすべてをここに捧げる

2024/02/08に公開

APIのMockを作る

Nuxtかどうかは正直あまり関係はない。APIの開発を待っている間、テスト的にAPIに対応した開発を進めていきたいと考えることは自然なことだろう。得にAPI開発が遅れている場合は、想定している問い合わせや返却結果など、先に実装していきたいと考えることが多い。

msw

mswは個人的にとても優れていると思っているAPIのMock機構だ。非常にシンプルで、わかりやすい。基礎的な部分はここで割愛するが、よりアカウント管理に近いものとして、用いたものを紹介する。

Cookies

まずはCookieだ。これについては、公式ドキュメントにも記載があるため、知っている人も多いだろう。
Cookieの読み取りは、引数で渡ってくるCookieを分割代入で受け取るのみだ。

  http.get('/api/user', ({ cookies }) => {
    if (!cookies.authToken) {
      return new HttpResponse(null, { status: 403 })
    }
    return HttpResponse.json({ name: 'John' })
  }),

オブジェクトのキーとしてそのまま参照できるのは非常にありがたい。クライアント側にCookieを渡す場合は、通常通り、Headerに定義すれば問題ない。このあたりは、受け取り同様に簡単な定義があるとなお良かった気はするが、Mockなのだから、ワガママは言えない。

    return new HttpResponse(null, {
      headers: {
        'Set-Cookie': 'authToken=abc-123',
      },
    })

擬似的なデータベース

いくらMockだと言っても、クライアント側からデータを送信したときに、その情報を保持しておいてほしいと思うことは多い。msw単体には標準でその機能はなく、mswjs/storageを導入する。軽く調べたときに、なぜかこれが検索にヒットしづらく、見つけるのに少しだけ時間をかけてしまった。
使い方はそれほど難しくなく、以下のように、保存場所の定義を行う。ジェネリック関数のため、TypeScriptによる型の設定も対応している。

import { LiveStorage } from '@mswjs/storage'
const posts = new LiveStorage('posts', [])

実際にリクエストを受ける処理にて、以下のようにPostで受け取った値を設定すれば、いつでも同じ内容を呼び出すことができる。ユーザーのIDなどと合わせて用いれば、配列のfilterメソッドなどで、取り出すことも容易だろう。

posts.update((prevPosts) => [...prevPosts, { title: 'Brave new world' }])

取り出す場合は、以下のように、メソッドを実行するだけだ。

posts.getValue();

もちろん配列で返却されるため、たとえば、検索用のAPIが必要なら、配列をフィルターすればいいし、ユーザー用の画面で削除等行うなら、除外する処理を行えばいいだろう。
データベースなど大層なことを扱わなくても、容易にMockにてデータの保持ができるのは、非常に嬉しい。

その他

テストフレームワークなどを使用する場合にダミーデータを使用できるmsw/dataも存在する。ここまで来ると、逆に実用的に使いたくなってしまう。それだけ素敵な仕組みだと思う。

Discussion