Spring Cloud Contract Groovy DSL如何定义请求体对象属性可空
解决方案1:单合约内置可空规则(推荐)
直接在Groovy DSL中用or()组合匹配规则,实现同一个字段既可以匹配指定结构体,也可以匹配null,无需维护多份合约,不会出现匹配优先级问题。修改后的合约示例如下:
Contract.make { description "Nullable sender & receiver API contract" request { method POST() url value(consumer(regex('/message'))) headers { contentType(applicationJson()) header("x-channelId", anyNonBlankString()) } body( sender: value(consumer(or( nullValue(), [ toEmail : anyEmail(), firstName : anyNonBlankString(), lastName : anyNonBlankString() ] ))), receiver: value(consumer(or( nullValue(), [ toEmail : anyEmail(), firstName : anyNonBlankString(), lastName : anyNonBlankString() ] ))) ) } response { status CREATED() } }
其中or()是DSL内置的匹配组合算子,nullValue()用于匹配JSON null值,两者组合后即可实现整个结构体可空的校验规则,2020.0.2版本对应的Spring Cloud Contract 3.0.x完全支持该写法。
解决方案2:多合约场景调整Stub优先级
如果你需要保留多份合约的写法,只需要给不同合约设置匹配优先级即可解决WireMock匹配错误的问题:WireMock会优先匹配优先级数值更小的Stub,你可以给规则越严格的合约设置越高的优先级:
- 两个字段都有值的合约设置
priority 1(最高优先级) - 单字段为null的合约设置
priority 2 - 两个字段都为null的合约设置
priority 3(最低优先级)
示例如下:
// 两个字段都有值的合约 Contract.make { priority 1 description "sender & receiver both not null" // 原有请求、响应定义 } // sender为null的合约 Contract.make { priority 2 description "sender is null" // 对应请求、响应定义 } // 以此类推剩余两种场景的合约
内容的提问来源于stack exchange,提问作者Václav
相关产品推荐
相关产品推荐

