软断言你也学不会
断言是测试用例的一部分,也是测试工程师开发测试用例的核心。断言通常集成在单元测试和集成测试中,断言分为硬断言和软断言。

硬断言是我们狭义上听到的普通断言:当用例运行后得到的[实际]结果与预期结果不匹配时,测试框架将停止测试执行并抛出断言错误。如下面的案例,测试执行在第一个失败时停止,即使测试中有更多的断言也不会继续执行。
import org.assertj.core.api.SoftAssertions;
import org.junit.jupiter.api.Test;class HardAssertionTest {@Testvoid hardAssertion() {var person = Person.builder().name("John").phoneNumber(null).age(16).build();assertThat(person.getName()).isNotBlank();assertThat(person.getPhoneNumber()).isNotNull();assertThat(person.getAge()).isGreaterThan(18);}
}
第10行断言失败,则第11行和第12行的断言将不会被执行。
java.lang.AssertionError:
Expecting actual not to be null
通常来说,硬断言在断言失败情况下终止测试执行是无可厚非的。但是在某些情况下,我们想知道被断言的“对象”里哪些属性是不符合预期的,这样使用软断言将解决这个问题。
什么是软断言?
软断言:当一个测试用例中存在多个断言,当有一个断言失败时,会执行后续的断言。
支持软断言的工具通常使用下面的伪代码实现。
SoftAssertion softAssertion = new SoftAssertion()softAssertion.assertSomething...
softAssertion.assertAnotherThing...
softAssertion.assertTheLastThing...softAssertion.assertThenAll();
什么情况下使用软断言?
当测试用例有多个断言时候,应该使用软断言。因为知道所有断言是否与预期结果一致,可以减少多次运行测试以了解哪些不通过。
当测试用例有不止一条断言时,软断言就要到位了。
支持软断言的工具

TestNG
TestNG有一个SoftAssert类,它的功能与前面介绍的伪代码相同:它对断言进行分组,并在我们调用特定方法时立即进行验证。

来看一个软断言的案例:
public class SoftAssertTestNGTest {@Testpublic void testNGSoftAssertion() {var person = Person.builder().name("John").phoneNumber(null).age(16).build();SoftAssert softAssert = new SoftAssert();softAssert.assertEquals(person.getName(), "John");softAssert.assertNotNull(person.getPhoneNumber(), "Phone number cannot be null");softAssert.assertEquals(person.getAge(), 25, "Age should be equal");softAssert.assertAll();}
}
在例子中,我们断言:phoneNumber不能为空,年龄必须等于25。
- 第8到10行使用softAssertion在断言方法之前,告诉代码它属于SoftAssertion类。可以使用TestNG支持的任何断言方法实现。
- 第12行调用assertAll ()方法,该方法将运行与softAssertion引用关联的所有断言
我们可以看到显示一个断言失败,而TestNG没有停止测试执行,而是运行所有的断言,显示所有的失败。
java.lang.AssertionError: The following asserts failed:Phone number cannot be null
Expected :25
Actual :16
<Click to see difference>
JUnit 5
JUnit 5使用assertAll()方法作为软断言方法。它不需要使用外部特定类,它已经是断言类的一部分。我们需要做的就是静态方式导入它。
例子:
import org.junit.jupiter.api.Test;import static org.junit.jupiter.api.Assertions.assertAll;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertNotNull;class SoftAssertionJunit5Test {@Testvoid softAssertionUsingJUnit5() {var person = Person.builder().name("John").phoneNumber(null).age(16).build();assertAll("person",() -> assertNotNull(person.getName(), "Name must not be null"),() -> assertNotNull(person.getPhoneNumber(), "Phone number should not be null"),() -> assertEquals(18., person.getAge(), "Age must be 18"));}
}
- 第12行显示了使用两个参数的assertAll()方法
-
- 一个标题
- 一个流式的可执行的命令,即断言方法
- 第13到15行显示了stream的用法,每个stream用于我们必须应用的任何断言
执行结果如下:
org.opentest4j.AssertionFailedError: Phone number should not be null ==> expected: not <null>at org.example.SoftAssertionJunit5Test.lambda$softAssertionUsingJUnit5$1(SoftAssertionJunit5Test.java:17)org.opentest4j.AssertionFailedError: Age must be 18 ==>
Expected :18.0
Actual :16.0at org.example.SoftAssertionJunit5Test.lambda$softAssertionUsingJUnit5$2(SoftAssertionJunit5Test.java:18)org.opentest4j.MultipleFailuresError: person (2 failures)org.opentest4j.AssertionFailedError: Phone number should not be null ==> expected: not <null>org.opentest4j.AssertionFailedError: Age must be 18 ==> expected: <18.0> but was: <16.0>
AssertJ
AssertJ断言库提供了软断言的不同方法,并可以创建自己的断言:
- 调用assertAll ()
- 使用autocloseableoftassertion
- 使用静态方法assertsoft
我们可以使用所有这些不同的方法来应用它,并在AssertJ页面上查看所有示例。这里可以看到assertsoft静态方法的使用案例。
import org.assertj.core.api.SoftAssertions;
import org.junit.jupiter.api.Test;class SoftAssertionTest {@Testvoid softAssertionUsingAssertJ() {var person = Person.builder().name("John").phoneNumber(null).age(16).build();SoftAssertions.assertSoftly(softly -> {softly.assertThat(person.getName()).isNotBlank();softly.assertThat(person.getPhoneNumber()).isNotNull();softly.assertThat(person.getAge()).isGreaterThan(18);});}
}
异常输出如下:
java.lang.AssertionError:
Expecting actual not to be null
at SoftAssertionTest.lambda$assertJSoftAssertion$0(SoftAssertionTest.java:16)java.lang.AssertionError:
Expecting actual:16
to be greater than:18
at SoftAssertionTest.lambda$assertJSoftAssertion$0(SoftAssertionTest.java:17)org.assertj.core.error.AssertJMultipleFailuresError:
Multiple Failures (2 failures)
-- failure 1 --
Expecting actual not to be null
at SoftAssertionTest.lambda$assertJSoftAssertion$0(SoftAssertionTest.java:16)
-- failure 2 --
Expecting actual:16
to be greater than:18
at SoftAssertionTest.lambda$assertJSoftAssertion$0(SoftAssertionTest.java:17)
- AssertionErrors列表及其完整的堆栈信息
- 带有断言失败的摘要信息
相关文章:
软断言你也学不会
断言是测试用例的一部分,也是测试工程师开发测试用例的核心。断言通常集成在单元测试和集成测试中,断言分为硬断言和软断言。 硬断言是我们狭义上听到的普通断言:当用例运行后得到的[实际]结果与预期结果不匹配时,测试框架将停止测试执行并抛…...
【推荐系统】多任务学习模型
介绍一些多任务学习模型了解是如何处理多任务分支的。 ESSM, Entire Space Multi-Task Model 阿里提出的ESSM全称Entire Space Multi-Task Model,全样本空间的多任务模型,有效地解决了CVR建模(转化率预估)中存在的两个非常重要…...
基于SpringBoot的商品物品产品众筹平台设计与实现(源码+lw+部署文档+讲解等)
文章目录 前言具体实现截图论文参考详细视频演示为什么选择我自己的网站自己的小程序(小蔡coding)有保障的售后福利 代码参考源码获取 前言 💗博主介绍:✌全网粉丝10W,CSDN特邀作者、博客专家、CSDN新星计划导师、全栈领域优质创作…...
《安富莱嵌入式周报》第323期:NASA开源二代星球探索小车, Matlab2023b,蓝牙照明标准NLC, Xilinx发布电机套件,Clang V17发布
周报汇总地址:嵌入式周报 - uCOS & uCGUI & emWin & embOS & TouchGFX & ThreadX - 硬汉嵌入式论坛 - Powered by Discuz! 视频版: https://www.bilibili.com/video/BV1vp4y1F7qD 《安富莱嵌入式周报》第323期:NASA开源…...
Redis的事务管理
redis也支持事务,但与MySQL等关系型数据库相比,redis的事务比较简单。 一、redis事务的特点 1、redis的事务是一组命令集合 可以把redis的事务看成一个命令的缓存,把一组要执行的命令添加到集合中,然后按顺序一起执行。 2、redi…...
openwrt (一):特殊的WiFi驱动移植方法
openwrt的去驱动移植灵活多样,总体来说只要掌握了官方提供的操作方法即可可简单上手,但是也有一些稍微比较特殊的操作。比如说backport模块。 由于需要兼容很多不同版本的Linux驱动,很多时候需要用到backport。因此,如果已有的项目…...
PCL 计算点云中值
目录 一、算法原理2、主要函数二、代码实现三、结果展示四、参考链接本文由CSDN点云侠原创,原文链接。如果你不是在点云侠的博客中看到该文章,那么此处便是不要脸的爬虫。 一、算法原理 计算点云坐标的中值点,首先对点云坐标进行排序,然后计算中值。如果点云点的个数为奇数…...
【工作记录】前后端分离场景下CAS单点登录的集成思路与实践@20230926
背景及目的 之前做一个公司项目的时候甲方要求集成他们指定的CAS服务端实现登录,要求不影响原有业务。 CAS服务端提供的文档都是基于前后端不分离的应用,对前后端分离应用没有任何说明,找官方人问也是爱答不理的,近期正好有时间就…...
阿里云数据库RDS有哪些?细数关系型数据库大全
阿里云RDS关系型数据库大全,关系型数据库包括MySQL版、PolarDB、PostgreSQL、SQL Server和MariaDB等,NoSQL数据库如Redis、Tair、Lindorm和MongoDB,阿里云百科分享阿里云RDS关系型数据库大全: 目录 阿里云RDS关系型数据库大全 …...
【计算机网络】因特网中的电子邮件
文章目录 简单邮件传送协议SMTP邮件访问协议POP3IMAPHTTP 参考资料 电子邮件为异步通信媒介 因特网电子邮件系统 电子邮件系统的三个构件:用户代理、邮件服务器、邮件发送和读取协议 用户代理 User Agent 即UA 电子邮件客户端软件,用户与电子邮件系统的接…...
【C++11】多线程
多线程创建线程thread提供的成员函数获取线程id的方式线程函数参数的问题线程join场景和detach 互斥量库(mutex)mutexrecursive_mutexlock_guard 和 unique_lock 原子性操作库(atomic)条件变量库(condition_varuable&a…...
【vue3】shallowReactive与shallowRef;readonly与shallowReadonly;toRaw与markRaw
假期第六篇,对于基础的知识点,我感觉自己还是很薄弱的。 趁着假期,再去复习一遍 1、shallowReactive与shallowRef shallowReactive:只处理对象最外层属性的响应式(浅响应式) shallowRef:只处理…...
手机建模教程 | 如何从易模App中导出模型?有哪些格式?含贴图吗?
很多小伙伴使用易模App是为了能快速地将已有实物的物体“变成”三维模型后转到自己习惯的3D软件中去编辑,于是,大家都关心模型能否导出,以及导出格式有没有自己想要的? 博雅仔告诉大家,当然可以导出! 在导出…...
数据分析技能点-机器学习优化思想
优化思想,这个听起来极其专业和高端的词汇,其实它无处不在,悄无声息地影响着我们的生活和决策。从寻找最快的上班路线,到决定如何配置投资组合,优化思想都是一个不可或缺的元素。而在机器学习领域,优化思想更是扮演着至关重要的角色。 文章目录 优化的基础优化问题与实际…...
应用架构的演进:亚马逊的微服务实践
当你在亚马逊上购物时,或许不会想到,你看到的这个购物网站,其背后技术架构经历了什么样的变迁与升级。 还记得上世纪 90 年代,那个只卖书的网上书店吗?那时的亚马逊,不过是一个架构简单的网站,所有的功能都堆积在一个庞大的软件堡垒里。随着更多业务的增加、更新和迭代,这个软…...
leetCode 55.跳跃游戏 贪心算法
给你一个非负整数数组 nums ,你最初位于数组的 第一个下标 。数组中的每个元素代表你在该位置可以跳跃的最大长度。判断你是否能够到达最后一个下标,如果可以,返回 true ;否则,返回 false 。 示例 1: 输入…...
CF505B Mr. Kitayuta‘s Colorful Graph
Mr. Kitayuta’s Colorful Graph 题面翻译 给出一个 n n n 个点, m m m 条边的无向图,每条边上是有颜色的。有 q q q 组询问 对于第 i i i 组询问,给出点对 u i , v i u_i,v_i ui,vi。求有多少种颜色 c c c 满足:有至…...
c#设计模式-结构型模式 之 组合模式
🚀简介 组合模式又名部分整体模式,是一种 结构型设计模式 ,是用于把一组相似的对象当作一个 单一的对象 。组合模式 依据树形结构来组合对象 ,用来表示部分以及整体层,它可以让你将对象组合成树形结构,并且…...
【Rust日报】2023-09-30 使用Rust做web抓取
CockroachDB 用rust重新实现 嘿,伙计们,我在 Rust 中实现了一个分布式 SQL 数据库。它就像 CockroachDB 和谷歌Google Spanner。告诉我你的想法。 注意: 这不是生产级别的数据库,这是一个以学习为目的的项目。有许多特性,但是缺少…...
【密评】商用密码应用安全性评估从业人员考核题库(三)
商用密码应用安全性评估从业人员考核题库(三) 国密局给的参考题库5000道只是基础题,后续更新完5000还会继续更其他高质量题库,持续学习,共同进步。 501 多项选择题 《个人信息保护法》要求个人信息处理者应当采取哪些…...
原子操作 CAS 与锁实现
原子操作 CAS 与锁实现 文章目录原子操作 CAS 与锁实现1. CPU 缓存架构与缓存一致性1.1 为什么需要 CPU 缓存?1.2 写回策略与缓存不一致问题1.3 缓存一致性协议:MESI 与总线嗅探2. 原子操作:不可分割的执行单元2.1 什么是原子操作?…...
Phi-3-vision-128k-instruct惊艳案例:宠物照片→品种识别+健康风险+喂养建议
Phi-3-vision-128k-instruct惊艳案例:宠物照片→品种识别健康风险喂养建议 1. 模型简介 Phi-3-Vision-128K-Instruct 是一款轻量级的多模态模型,专注于高质量的文本和视觉数据处理。作为 Phi-3 模型家族的一员,它支持长达128K的上下文长度&…...
Thinkphp和Laravel框架微信小程序的 畅玩安阳旅游网站平台的景点门票民宿预订-
目录技术选型与框架整合数据库设计接口开发微信支付集成性能优化与安全测试与部署项目技术支持可定制开发之功能创新亮点源码获取详细视频演示 :文章底部获取博主联系方式!同行可合作技术选型与框架整合 ThinkPHP和Laravel均可作为后端框架实现微信小程…...
OFA-VE一键部署教程:3分钟搭建赛博风格分析系统
OFA-VE一键部署教程:3分钟搭建赛博风格分析系统 1. 开篇:为什么选择OFA-VE? 如果你正在寻找一个既酷炫又实用的视觉分析工具,OFA-VE绝对值得一试。这个来自阿里巴巴达摩院的技术,能够智能分析图像和文本之间的逻辑关…...
Phi-3-vision-128k-instruct智能助手:支持微信截图/钉钉群聊图的办公效率增强工具
Phi-3-vision-128k-instruct智能助手:支持微信截图/钉钉群聊图的办公效率增强工具 1. 模型简介 Phi-3-Vision-128K-Instruct是一款轻量级的多模态智能助手,专为提升办公效率而设计。这个模型最突出的特点是能够理解图片中的内容,特别适合处…...
Nat Methods | 哈工大王亚东/程亮团队开发通用反卷积深度学习框架,实现转录组、蛋白质组、代谢组细胞数据精准解析
细胞丰度是指组织内各类细胞类型的比例分布,其动态变化在器官发育、基因调控和疾病治疗等生物学过程中至关重要。尽管单细胞技术能直接解析细胞异质性,但其成本较高、样本处理受限,难以大规模应用于临床队列研究,且大量珍贵的组织…...
架构自定义UDP协议视频传输调试
一、整体系统架构图┌─────────────────────────────────────────────────────────────────┐ │ 视频流应用程序 │ │ test_…...
open claw安装后启动运行web UI界面 - wsl版
以管理员身份打开 PowerShell 查看wsl中安装的发行版 wsl --list --verbose进入打wsl中指定的发行版 wsl -d Ubuntu查看 Gateway 状态 openclaw gateway status启动服务(通过 systemd/launchd) openclaw gateway start查看基础的网页端 openclaw gateway…...
openclaw飞书机器人权限管理
为了确保 OpenClaw 既能顺畅运行,又不至于因权限过大导致安全隐患,建议在飞书开发者后台 - 权限管理中,按照以下清单进行勾选。 这份清单分为基础必备和进阶功能两部分: 基础必备权限(无论个人还是团队,必须…...
GEO,AI界的“大冤种”
技术的迭代,AI已经不单纯是内容的创作者,它在演变为经济活动的独立参与者。在自主代理技术的加持夏,这个看似完美的自动化商业闭环中,却出现了极具讽刺的一幕,聊天机器人自己投放广告,流量产生了点击发生了…...
