Microserviceのテストの話を調べていると、以下のような記事を見つけました。
Simplifying Micro-Service testing with Pacts
このPactoと呼ばれるツールがConsumer Driven Contractsと呼ばれるデザインパターンを使っていると書いていたので、同デザインパターンを少し調べてみました。
関連:
- MartinFowler氏のブログ記事
- Pactoに関するGitHub
- デザインパターンとしての説明
- 消費者主導契約を使ったサービス指向開発
Consumer-Driven Contracts Design Patternをざっくりいうと
Consumer-Driven Contract patternは、Consumerが取得可能な必要なサービスをProviderと共有(規約)し、Customerごとに特定のサービスのみをProviderから利用可能にするパターンです。
特定のCustomerが使う機能をProviderから取得することで、Customerは限定された範囲の機能を利用します。CustomrはProviderにより提供されるであろう機能の取得を試み、契約(Contract)を成立させようとします。このとき、Customerが利用する機能の補助的な説明をProviderに提供することもできます。ここで契約が正常に成立すると、サービス実行時には基本的にCustomerは契約の成立した機能を使ってProviderからサービスを受けます。
Customerが使っている機能はProviderに適宜提供されます。ProviderはすべてのCustomerが利用している機能の規約の集合をもちます。
登場人物
- Provider contracts
- Providorから提供されているサービスに関する規約。XMLなどで記載される。
- Consumer contracts
- Provider Contractのうち、個々のCustomerが必要とする範囲の規約
- 個々の消費者が必要とするサービスの契約
- Consumer-Driven Contracts(消費者主導契約)
- Service Providerが満たすべき全Consumer Contractsの集合を書いた規約
Summary of Contract Characteristics
MarfinFowler氏の記事のなかで、Provider,Consumer,Consumer-Drivenのそれぞれがどのような関係を持つものかをまとめたもの。
Contract | Open | Complete | Number | Authority | Bounded |
---|---|---|---|---|---|
Provider | Closed | Complete | Single | Authoritative | Space/time |
Consumer | Open | Incomplete | Multiple | Non-authoritative | Space/time |
Consumer-Driven | Closed | Complete | Single | Non-authoritative | Consumers |
Pactsを使ったテスト
CustomerやService Providorに対するHTTPリクエスト/レスポンスをPactsが模倣して、その結果をRSpecを使いバリデーションする。そうすることで、Consumer-Driven Contracts Design Patternに登場してくる要素に対するテストを実施できるようにしているっぽい。
締め
SOAやMicroserviceでは、各々のサービスの依存関係や関係性が開発の妨げになることがおおいにあります。そいうのも、依存関係を持つサービスであれば、同時にデプロイするなどのように タイミング揃える ことが必要になるためです。それでは、高い開発速度を、それぞれのサービスチームが維持できません。
それに対して、このConsumer-Driven Contracts Design Patternは依存関係をデプロイ後に取得することでそのサービス同士の関係性を緩和させることが目的のようです。言われれば確かなのですが、これをちゃんと実装、運用するにはシステムの設計だったり、そのテストの構築が大変そう。
ともあれ、Service Discoveryのような位置付けですね。なるほど。