首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >比较两个忽略空值的对象

比较两个忽略空值的对象
EN

Stack Overflow用户
提问于 2020-05-07 14:55:20
回答 3查看 2.9K关注 0票数 2

该项目使用TestNg,Java11,Spring测试

我正在为API编写testNG测试,我有一个具有这种结构的java对象:

代码语言:javascript
复制
class Object1
    private Object2 o2;
    private List<Object3> o3;

其中Object2不仅由原始属性组成。

我想测试一下2 Object1是否与以下规则相等:

  • 如果实际的o2为空,即使其他o2不是空的,也不要失败。
  • 如果实际o3为空或空,即使其他o3不为空,也不要失败
  • 如果实际o3不为空或为空,则只比较非空Object3字段

总之,我想断言两个对象是相同的,递归地忽略了空字段。

我能做到

代码语言:javascript
复制
assertThat(actual).usingRecursiveComparison().ignoringActualNullFields().isEqualTo(other);

但递归空字段不会被忽略。

我怎么才能解决这个问题?

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2020-06-04 07:56:55

我终于创造了我自己的断言如下:

代码语言:javascript
复制
import org.assertj.core.api.AbstractAssert;
import org.assertj.core.api.Assertions;

import java.util.List;
import java.util.stream.Collectors;

public class Object1Assert extends AbstractAssert<Object1Assert, Object1> {

    public Object1Assert isEqualTo(Object1 other) {

        // specially for null
        if(actual == other) {return this;}

        if(actual.getObject2() != null) {
            Assertions.assertThat(other.getObject2()).isEqualToIgnoringNullFields(actual.getObject2());
        }

        if(actual.getObject3() != null) {
            for(Object3 object3 : actual.getObject3()) {
                my.package.Assertions.assertThat(object3).isIn(other.getObject3());
            }
        }
        // return the current assertion for method chaining
        return this;
    }

    public Object1Assert(Object1 actual) {
        super(actual, Object1Assert.class);
    }

    public static Object1Assert assertThat(Object1 actual) {
        return new Object1Assert(actual);
    }

}
代码语言:javascript
复制
public class Assertions {

    public static Object3Assert assertThat(Object3 actual) {
        return new Object3Assert(actual);
    }
}
代码语言:javascript
复制
public class Object3Assert extends AbstractAssert<Object3Assert, Object3> {

    public Object3Assert isIn(List<Object3> others) {
        List<String> otherStringIds = others.stream().map(Object3::getStringId).collect(Collectors.toList());
        Assertions.assertThat(otherStringIds).isNotEmpty();
        Assertions.assertThat(actual.getStringId()).isIn(otherStringIds);
        for (Object3 otherObject3 : others) {
            if(actual.getStringId().equalsIgnoreCase(otherObject3.getStringId())) {
                Assertions.assertThat(otherObject3).usingComparatorForType(Comparators.bigDecimalComparator, BigDecimal.class).isEqualToIgnoringNullFields(actual);
            }
        }
        // return the current assertion for method chaining
        return this;
    }

    public Object3Assert(Object3 actual) {
        super(actual, Object3Assert.class);
    }

    public static Object3Assert assertThat(Object3 actual) {
        return new Object3Assert(actual);
    }

}

我使用本教程https://www.baeldung.com/assertj-custom-assertion为所需的每种类型创建了这个类。

票数 0
EN

Stack Overflow用户

发布于 2020-05-08 03:15:49

您也可以忽略期望空字段。

你还能提供一个简单的测试来重现这个问题吗?请随意在https://github.com/joel-costigliola/assertj-core/issues中提出一个问题

票数 0
EN

Stack Overflow用户

发布于 2020-05-09 15:32:39

对我来说,下面的代码奏效了:

代码语言:javascript
复制
public class SocialLink {
    private String platform;
    private String link;
}

SocialLink obj1 = new SocialLink("Facebook", null);
SocialLink obj2 = new SocialLink("Facebook", null);

assertThat(obj1).isEqualToIgnoringNullFields(obj2);
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/61660918

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档