如何使用 AssertJ 递归比较具有不同字段名称但具有相同值的两个对象
How to recursively compare two objects with different field names but same values with AssertJ
我想使用 AssertJ 的递归比较来比较两个对象(DTO 和一个实体),以便对 DTO-> 实体映射器进行单元测试。
这两个对象都具有值几乎相同的字段,但是这两个对象之间的某些字段具有不同的名称。这会导致以下错误:
DTO can't be compared to Entity as Entity does not declare all DTO fields, it lacks these: [dtoFieldA, dtoFieldB, dtoFieldC]
我试过以下配置,但没有成功:
assertThat(DTO)
.usingRecursiveComparison(RecursiveComparisonConfiguration.builder()
.withEqualsForFields(fieldAPRedicate, "dtoFieldA")
.withEqualsForFields(fieldBPRedicate, "dtoFieldB")
.withEqualsForFields(fieldCPRedicate, "dtoFieldC")
.build())
.isEqualTo(Entity)
BiPredicate<DTO, Entity> fieldAPRedicate = (d, e) -> d.dtoFieldA().equals(e.entityFieldA());
BiPredicate<DTO, Entity> fieldBPRedicate = (d, e) -> d.dtoFieldB().equals(e.entityFieldB());
BiPredicate<DTO, Entity> fieldCPRedicate = (d, e) -> d.dtoFieldC().equals(e.entityFieldC());
比较类:
DTO:
public class DTO {
protected String sameNameField1;
protected String sameNameField2;
protected String dtoFieldA;
protected String dtoFieldB;
protected String dtoFieldC;
}
实体:
public class Entity {
protected String sameNameField1;
protected String sameNameField2;
protected String entityFieldA;
protected String entityFieldB;
protected String entityFieldC;
}
如何为这种情况配置 assertJ?
我认为你目前能做的最好的事情就是忽略字段,因为在递归比较中不支持比较不同名称的字段,忽略 doc:https://assertj.github.io/doc/#assertj-core-recursive-comparison-ignoring-fields
如果您绝对需要将 DTO.a
字段与 Entity.b
字段进行比较,最好的选择是定义一个自定义比较方法,该方法可以知道将哪个字段与哪个字段进行比较,但是什么也没有在 AssertJ 中做事真的很有帮助(usingComparison()
存在,但通用类型不允许将您的 DTO 与实体进行比较,除非您将所有内容都用 Object 处理,但此时解决方法不再值得了)。
我想使用 AssertJ 的递归比较来比较两个对象(DTO 和一个实体),以便对 DTO-> 实体映射器进行单元测试。 这两个对象都具有值几乎相同的字段,但是这两个对象之间的某些字段具有不同的名称。这会导致以下错误:
DTO can't be compared to Entity as Entity does not declare all DTO fields, it lacks these: [dtoFieldA, dtoFieldB, dtoFieldC]
我试过以下配置,但没有成功:
assertThat(DTO)
.usingRecursiveComparison(RecursiveComparisonConfiguration.builder()
.withEqualsForFields(fieldAPRedicate, "dtoFieldA")
.withEqualsForFields(fieldBPRedicate, "dtoFieldB")
.withEqualsForFields(fieldCPRedicate, "dtoFieldC")
.build())
.isEqualTo(Entity)
BiPredicate<DTO, Entity> fieldAPRedicate = (d, e) -> d.dtoFieldA().equals(e.entityFieldA());
BiPredicate<DTO, Entity> fieldBPRedicate = (d, e) -> d.dtoFieldB().equals(e.entityFieldB());
BiPredicate<DTO, Entity> fieldCPRedicate = (d, e) -> d.dtoFieldC().equals(e.entityFieldC());
比较类:
DTO:
public class DTO {
protected String sameNameField1;
protected String sameNameField2;
protected String dtoFieldA;
protected String dtoFieldB;
protected String dtoFieldC;
}
实体:
public class Entity {
protected String sameNameField1;
protected String sameNameField2;
protected String entityFieldA;
protected String entityFieldB;
protected String entityFieldC;
}
如何为这种情况配置 assertJ?
我认为你目前能做的最好的事情就是忽略字段,因为在递归比较中不支持比较不同名称的字段,忽略 doc:https://assertj.github.io/doc/#assertj-core-recursive-comparison-ignoring-fields
如果您绝对需要将 DTO.a
字段与 Entity.b
字段进行比较,最好的选择是定义一个自定义比较方法,该方法可以知道将哪个字段与哪个字段进行比较,但是什么也没有在 AssertJ 中做事真的很有帮助(usingComparison()
存在,但通用类型不允许将您的 DTO 与实体进行比较,除非您将所有内容都用 Object 处理,但此时解决方法不再值得了)。