11
11

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

Shinjuku.LTAdvent Calendar 2018

Day 17

gRPCのMock戦略

Last updated at Posted at 2018-12-16

はじめに

API開発において、サーバとクライアントが別れて開発することは多いと思います。
しかし、そのような場合にクライアントが平行、あるいは先行して開発をすることになると、必要となるサーバが存在しないため開発がしにくくなります。
そこで出てくるのがAPIのモックサーバです。

Dev Mock

クライアント開発時、本物のサーバの代わりにモックサーバを利用し開発を行い、サーバの開発が完了した時点で結合を行うようにします。

ここではよくあるREST APIと比較したgRPCのMockについて記載します。

REST APIのモックサーバ

RESTのモックサーバはホスティングサービスから、単体のツールまで沢山あるので、ここではシンプルなjson-serverを例にしたいと思います。

json-serverによるモック

json-serverを利用した開発は簡単で、レスポンスとなるjsonを定義し、json-serverに読み込ませるだけです。

Terminal
> npm install -g json-server
db.json
{
  "posts": [
    { "id": 1, "title": "json-server", "author": "typicode" }
  ],
  "comments": [
    { "id": 1, "body": "some comment", "postId": 1 }
  ],
  "profile": { "name": "typicode" }
}
Terminal
> json-server --watch db.json

また、CRUD処理やソート、ページングなどもjson-serverの仕組みに乗ることで利用が可能です。

クライアント開発では、事前にjsonの定義でサーバ相当の機能を実現、開発し、サーバ開発が完了した時点で本物のサーバを利用するようにします。

gRPCのモックサーバ

gRPCの開発スタイル

Kobito.XIS1od.png

gRPCにおける開発では概ね以下のフローで行います。

  1. クライアント/サーバ間のインターフェイス定義
  2. protocにより、クライアント/サーバの自動生成
  3. サーバ側の実装
  4. クライアントからサーバの利用

ここで重要なのが、2.クライアント/サーバの自動生成です。

言語依存はありますが、ここで生成されるサーバのコードはほぼそのままサーバとして実行が可能なコードが生成されます。
つまり、RESTでいうjson-serverのような仕組みが公式でサポートされています。

また、生成するサーバのコードも任意の言語で自動生成可能なので、クライアントを実装する開発者が扱いやすい言語のモックサーバで開発が可能です。

ということで、gRPCだと多くの場合、外部のMockツールがなくてもクライアントだけの開発が可能になります。

より簡単にgRPCのモックサーバを

gRPCの開発フローに乗ると、サーバ生成は簡単に行えるようになりますが、RESTのときと比べるとサーバ生成がちょっと手間に感じるかもしれません。
そんなときに便利なのが、Protobuf.jsのdynamic codegenです。

Protobuf.jsを使うとprotoファイルを直接読み込み、モック化したい処理の実装することで、1つのjsファイルだけでモックサーバが用意できます。
後は通常のnodeアプリケーションと同様起動するだけです。

server.js
// proto定義の読み込み
const PROTO_PATH = __dirname + '/../../protos/helloworld.proto'
const grpc = require('grpc')
const protoLoader = require('@grpc/proto-loader')
const packageDefinition = protoLoader.loadSync(/* ... */)
const hello_proto = grpc.loadPackageDefinition(packageDefinition).helloworld

// モック
function sayHello(call, callback) {
  callback(null, {message: 'Hello ' + call.request.name})
}

// サーバの設定
function main() {
  const server = new grpc.Server()
  // モックの組み込み
  server.addService(hello_proto.Greeter.service, {sayHello: sayHello})
  server.bind('0.0.0.0:50051', grpc.ServerCredentials.createInsecure())
  server.start()
}

main()
Terminal
> node server.js

単純なnodeのスクリプトになっているので、固定値を返すモックだけでなく、動的な処理を埋め込むのにも便利です。

RESTとのgRPCのMock比較

簡単に比較すると以下の特徴があります。

REST gRPC
機能 シンプルなものから高機能なものまで様々
用途に合わせて選択可能
本物のサーバと同様の機能を実現可能
使い慣れた言語でコントロール
拡張性 DSLや拡張機能、各種設定 使い慣れた言語で拡張できる
学習コスト 学習コストが低いものは機能や拡張性が低く、高機能だと学習コストが上がりやすい gRPCサーバの基礎知識があればよい
保守性 APIの定義を保証する仕組みがないため、別ツールと組み合わせるか、テストなどを行う必要がある スキーマ定義の仕組みが公式サポートのため、インターフェイスが保証されている

※ RESTのモックサーバはツールに依存します

まとめ

gRPCは提供されている仕組みそのものが、Mock機能も兼ねているのでその仕組みに乗るのが便利です!

参考

11
11
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
11
11

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?