| 
         对于最新的稳定版本,请使用 spring-cloud-contract 4.2.1!  | 
    
Stub Runner 核心
存根运行器核心为服务协作者运行存根。将存根视为 services 允许您使用 stub-runner 作为 Consumer 驱动的 Contract 的实现。
Stub Runner 允许您自动下载提供的依赖项的存根(或 从 Classpath 中选择它们),为它们启动 WireMock 服务器,并为它们提供适当的 存根定义。对于消息传递,定义了特殊的存根路由。
检索存根
您可以从以下获取存根的选项中进行选择:
- 
基于 Aether 的解决方案,可从 Artifactory 或 Nexus 下载带有存根的 JAR
 - 
Classpath-scanning 解决方案,它使用模式搜索 Classpath 以检索存根
 - 
编写您自己的
org.springframework.cloud.contract.stubrunner.StubDownloaderBuilder用于完全定制 
后一个示例在 Custom Stub Runner 部分中介绍。
下载 Stub
您可以使用stubsMode开关。它从StubRunnerProperties.StubsMode列举。您可以使用以下选项:
- 
StubRunnerProperties.StubsMode.CLASSPATH(默认值):从 Classpath 中选择存根 - 
StubRunnerProperties.StubsMode.LOCAL:从本地存储中选取存根(例如.m2) - 
StubRunnerProperties.StubsMode.REMOTE:从远程位置选取存根 
以下示例从本地位置选取存根:
@AutoConfigureStubRunner(repositoryRoot="https://foo.bar", ids = "com.example:beer-api-producer:+:stubs:8095", stubsMode = StubRunnerProperties.StubsMode.LOCAL)
类路径扫描
如果将stubsModeproperty 设置为StubRunnerProperties.StubsMode.CLASSPATH(或从CLASSPATH是默认值),则会扫描 Classpath。
请考虑以下示例:
@AutoConfigureStubRunner(ids = {
    "com.example:beer-api-producer:+:stubs:8095",
    "com.example.foo:bar:1.0.0:superstubs:8096"
})
您可以将依赖项添加到 Classpath 中,如下所示:
<dependency>
    <groupId>com.example</groupId>
    <artifactId>beer-api-producer-restdocs</artifactId>
    <classifier>stubs</classifier>
    <version>0.0.1-SNAPSHOT</version>
    <scope>test</scope>
    <exclusions>
        <exclusion>
            <groupId>*</groupId>
            <artifactId>*</artifactId>
        </exclusion>
    </exclusions>
</dependency>
<dependency>
    <groupId>com.example.thing1</groupId>
    <artifactId>thing2</artifactId>
    <classifier>superstubs</classifier>
    <version>1.0.0</version>
    <scope>test</scope>
    <exclusions>
        <exclusion>
            <groupId>*</groupId>
            <artifactId>*</artifactId>
        </exclusion>
    </exclusions>
</dependency>
testCompile("com.example:beer-api-producer-restdocs:0.0.1-SNAPSHOT:stubs") {
    transitive = false
}
testCompile("com.example.thing1:thing2:1.0.0:superstubs") {
    transitive = false
}
然后扫描 Classpath 上的指定位置。为com.example:beer-api-producer-restdocs,
将扫描以下位置:
- 
/META-INF/com.example/beer-api-producer-restdocs/*/.*
 - 
/contracts/com.example/beer-api-producer-restdocs/*/.*
 - 
/mappings/com.example/beer-api-producer-restdocs/*/.*
 
为com.example.thing1:thing2,则会扫描以下位置:
- 
/META-INF/com.example.thing1/thing2/*/.*
 - 
/contracts/com.example.thing1/thing2/*/.*
 - 
/mappings/com.example.thing1/thing2/*/.*
 
| 在打包 producer stub 的 | 
为了实现正确的存根打包,生产者将按如下方式设置 Contract:
└── src
    └── test
        └── resources
            └── contracts
                └── com.example
                    └── beer-api-producer-restdocs
                        └── nested
                            └── contract3.groovy
通过使用Maven 系列assembly插件或 Gradle Jar 任务,您必须创建以下内容
结构中:
└── META-INF
    └── com.example
        └── beer-api-producer-restdocs
            └── 2.0.0
                ├── contracts
                │   └── nested
                │       └── contract2.groovy
                └── mappings
                    └── mapping.json
通过维护此结构,可以扫描 Classpath,您可以从消息传递或 HTTP 存根,而无需下载构件。
配置 HTTP 服务器存根
Stub Runner 有一个HttpServerStub抽象出底层
HTTP 服务器的具体实现(例如,WireMock 是其中一种实现)。
有时,您需要对存根服务器执行一些额外的调整(这对于给定的实现是具体的)。
为此,Stub Runner 为您提供
这httpServerStubConfigurer属性,以及
JUnit 规则,可通过系统属性进行访问,您可以在其中提供
您对org.springframework.cloud.contract.stubrunner.HttpServerStubConfigurer接口。实现可以改变
给定 HTTP 服务器存根的配置文件。
Spring Cloud Contract Stub Runner 附带一个实现,您可以
可以扩展为 WireMock:org.springframework.cloud.contract.stubrunner.provider.wiremock.WireMockHttpServerStubConfigurer.
在configure方法
您可以为给定的存根提供自己的自定义配置。用途
case 可能会在 HTTPS 端口上为给定的项目 ID 启动 WireMock。以下内容
示例展示了如何做到这一点:
@CompileStatic
static class HttpsForFraudDetection extends WireMockHttpServerStubConfigurer {
	private static final Log log = LogFactory.getLog(HttpsForFraudDetection)
	@Override
	WireMockConfiguration configure(WireMockConfiguration httpStubConfiguration, HttpServerStubConfiguration httpServerStubConfiguration) {
		if (httpServerStubConfiguration.stubConfiguration.artifactId == "fraudDetectionServer") {
			int httpsPort = TestSocketUtils.findAvailableTcpPort()
			log.info("Will set HTTPs port [" + httpsPort + "] for fraud detection server")
			return httpStubConfiguration
					.httpsPort(httpsPort)
		}
		return httpStubConfiguration
	}
}
然后,您可以通过@AutoConfigureStubRunner注解,如下所示:
@AutoConfigureStubRunner(mappingsOutputFolder = "target/outputmappings/",
		httpServerStubConfigurer = HttpsForFraudDetection)
每当找到 HTTPS 端口时,它优先于 HTTP 端口。
运行 stub
本节介绍如何执行 stub。它包含以下主题:
HTTP 存根
存根在 JSON 文档中定义,其语法在 WireMock 文档中定义。
以下示例在 JSON 中定义一个存根:
{
    "request": {
        "method": "GET",
        "url": "/ping"
    },
    "response": {
        "status": 200,
        "body": "pong",
        "headers": {
            "Content-Type": "text/plain"
        }
    }
}
查看已注册的映射
每个存根协作者都会在__/admin/端点。
您还可以使用mappingsOutputFolder属性将映射转储到文件中。
对于基于注释的方法,它类似于以下示例:
@AutoConfigureStubRunner(ids="a.b.c:loanIssuance,a.b.c:fraudDetectionServer",
mappingsOutputFolder = "target/outputmappings/")
对于 JUnit 方法,它类似于以下示例:
@ClassRule @Shared StubRunnerRule rule = new StubRunnerRule()
			.repoRoot("https://some_url")
			.downloadStub("a.b.c", "loanIssuance")
			.downloadStub("a.b.c:fraudDetectionServer")
			.withMappingsOutputFolder("target/outputmappings")
然后,如果您查看target/outputmappings文件夹中,您将看到以下结构;
.
├── fraudDetectionServer_13705
└── loanIssuance_12255
这意味着注册了两个存根。fraudDetectionServer在端口注册13705和loanIssuance在端口12255.如果我们查看其中一个文件,我们将看到(对于 WireMock)
可用于给定服务器的映射:
[{
  "id" : "f9152eb9-bf77-4c38-8289-90be7d10d0d7",
  "request" : {
    "url" : "/name",
    "method" : "GET"
  },
  "response" : {
    "status" : 200,
    "body" : "fraudDetectionServer"
  },
  "uuid" : "f9152eb9-bf77-4c38-8289-90be7d10d0d7"
},
...
]