しおしお

IntelliJ IDEAのことなんかを書いてます

Spring Cloud Contractのstubをもとにサーバを起動してみる

Spring Cloud Contractを試してみた - しおしおの続きで、Producer側で生成したstubsをサーバとして起動してエンドポイントを叩いて結果が取得できるか試してみました。

Spring Cloud Contractを適用したプロジェクトの作成

新規でプロジェクトを作るのは大変なので、Spring Cloud Contractを試してみた - しおしおで作ったプロジェクトを使っていきたいと思います。

プロジェクトは、GitHubにいるので↓でcloneしてきます。

git clone git@github.com:siosio/spring-cloud-contract-example.git

Producer側でstubを生成する

generateClientStubsタスクを実行することで、stubを生成できます。 生成されたファイルは、build/stubs:/contracts/stubs配下にあります。

サンプルプロジェクトの場合、プロジェクト直下で↓を実行することで生成できます。

./gradlew server-service:generateClientStubs

生成したstubをもとにサーバを起動する

springcloud/spring-cloud-contract-stub-runnerイメージを使って、コンテナを起動できます。

環境変数に渡す値は、基本はAutoConfigureStubRunnerと同じ値になります。 大きく異なるのは、生成したstubをもとにサーバを起動したいので、STUBRUNNER_REPOSITORY_ROOTにはローカルのディレクトリを指定します。 指定した、ディレクトリには生成したstubが格納されているディレクトリの内容をコピーしておきます。

docker run  --rm \
  -e "STUBRUNNER_IDS=siosio:server-service:1.0.0:8080" \
  -e "STUBRUNNER_REPOSITORY_ROOT=stubs://file:///contracts/stubs/" \
  -e "STUBRUNNER_STUBS_MODE=LOCAL" \
  -p "8080:8080" \
  -v `pwd`/server-service/build/stubs:/contracts/stubs \
  springcloud/spring-cloud-contract-stub-runner:2.2.5.RELEASE

stubベースのサーバにアクセスしてみる

CDCの内容

CDCの内容的に、/sample/{数値}のエンドポイントを叩けば、stubが結果を返してくれるはずです。

import org.springframework.cloud.contract.spec.Contract

Contract.make {
  priority 2
  request {
    method('GET')
    url "/sample/${regex('\\d+')}"
  }

  response {
    status(OK())

    headers {
      contentType(applicationJson())
    }
    
    body(
        id: fromRequest().path(1),
        name: "name_${fromRequest().path(1)}"
    )
  }
}

実行結果

CDCの契約に従って、サーバが結果を返してくれていることが確認できますね。

$ curl http://localhost:8080/sample/1
{"id":"1","name":"name_1"}
$ curl http://localhost:8080/sample/123
{"id":"123","name":"name_123"}

これで、Producer側の開発が終わっていないタイミングでも、早いタイミングでインタフェースを確定してしまえば、stubベースのサーバを使ったConsumer側の開発ができそうな感じがありますね。