我有一个很少被重现的错误,在5次尝试中大约有1次(可再现性为20%)。开发人员使用此修复程序制作了新版本。我需要运行几次测试才能确定该错误已修复?该错误是主要的甚至是严重的,因此应格外小心地对其进行测试。我无法编写自动测试,因为这是一个复杂的场景。

评论

听起来像拉塞尔的茶壶也进入了软件工程;)

几年前,我有一个项目,其中设备上带有自定义固件的设备上的以太网芯片将平均连续3个月随机锁定一次,除非该项目涉及100个设备,所以总体上平均每天。它也是特定于站点的,我们从未在商店挂过任何设备,并且整整一年都对20台设备进行了连续测试。调试的唯一方法是在发生问题时附加硬件调试器。重新启动电源可以解决该问题。进入需要进行一周的规划,并需要获得许可的叉车操作员。 ...

...每次我们用调试器一枪都没有得到任何信息时,它要花费数千美元的人工,访问许可和费用,而且我们必须经历所有计划全新计划的繁琐工作访问访问,然后重试。直到今天,我们仍未解决问题。最好的工作原理是特定地点的EMI与不幸的PCB走线布局相结合。最后,如果一段时间没有看到网络数据,我只是让设备自行重启。一个噩梦般的结局令人沮丧的结局,有时仍然让我彻夜难眠。

@JasonC将数十亿美元的系统绑在一起的胶带和鸡丝的数量令人难以置信。
密切相关:sqa.stackexchange.com/q/28135/17060

#1 楼

您永远无法百分百地确定很少有可复制的错误已得到修复,只能接近99.9999999 ...%复制过程一遍又一遍,记录了您(希望!)没有遇到此问题的次数。错误没有得到修复,但只是没有发生。

在第二个测试中,现在有0.8 * 0.8 = 0.64(64%)的可能性没有得到修复但没有得到修复

在第三处:0.8 ^ 3 = 0.512 = 51.2%的错误未修复但没有发生的可能性。感到您的自信足够好。您将其描述为潜在的严重问题,因此99.5%可能是您的最低置信度限制。
为此,请进行24个测试。这将使您有0.8 ^ 24 = 0.004722(0.47%)的机会未修复且没有发生错误。

为99.9%的置信度,您需要进行31个测试。

评论


谢谢您的编辑!简单的错字可能会误导多远...

–杰克·特纳(Jake Turner)
17年3月30日在15:24

我想16次重复就足够了。 97%的概率是足够的。非常感谢你。

–nick_gabpe
17年3月30日在16:04

别客气。有关间歇性错误的更多信息,此博客文章中有一些精彩之处

–杰克·特纳(Jake Turner)
17 Mar 30 '17 at 16:10

我要强调的是,所有这些都假设1/5是一个强大的数据点,您知道该错误确实确实在20%的时间发生,这似乎有些不确定。作为一名测试人员,我真的会努力寻找被确定为漏洞的根本原因,并且知道,我能否100%地重现它?代码更改了吗,所以我无法再复制?

–ernie
17 Mar 30 '21:13



这种方法的问题有两个方面:1)如果您不知道如何触发错误,则测试方法可能会完全错过触发,因此将其建模为独立实验的可能性为20%这是有问题的,并且2)尝试进行的错误修复根本不可能没有任何效果,主要的危险是,他们将修复导致该错误的某些情况,而忽略了仍然导致该错误的某些极端情况。在那种情况下,该错误的发生率会降低,仅表明它在20%的时间中没有发生就几乎没有。

– John Coleman
17年4月1日在16:29

#2 楼

概率论上,杰克当然是正确的。

但是,计算机是确定性机器,因此,当您说您只能在1/5的时间内重现问题时,您真正要说的是,您实际上只是在创造一种情况,导致出现问题的时间为1/5。您需要与开发人员交谈,以更好地了解问题所在,导致问题发生的原因以及他为解决此问题所做的工作。

因为这就是我要做的更多关注。他是否能够将问题跟踪到特定的代码/功能/原因行,并进行修复,并添加测试用例以确保将来不再发生此问题,或者他是否在此过程中做了一些记录问题,也许通过增加另一层恢复?两者都会使问题消失,但是只有一个正在解决问题。 (并且取决于问题的严重性,发现问题的位置以及问题的性质,短期内解决问题可能是对的,但从长远来看可能不是。) >
理想情况下,开发人员应该能够告诉您是什么使1/5的时间与其他4/5的时间不同,并且您应该能够使用该信息来增加您的机会将问题的发生率提高到20%以上,甚至可能达到100%。然后您可以确定问题已解决,而不是几乎确定问题已解决。

评论


非常正确。修复它的开发人员还应该能够改善“重现步骤”,以便您可以在旧版本上100%的时间生成问题,在新版本上0%的时间生成问题。

–通配符
17 Mar 30 '17 at 18:37

很多时候这是正确的,但并非总是如此。同步错误是一个很大的例外。如果错误是由竞赛条件引起的,那么很难一直操纵竞赛来触发错误。

– Leliel
17 Mar 30 '17 at 20:42

+1。现在,开发人员更加了解错误的真正原因。他们应该能够指导您。如果没有其他问题,他们应该能够确认错误确实是随机的(而不是由特定的用户行为引起的),这将使Jake的答案有效。

–Cort Ammon
17 Mar 30 '17 at 20:59

代码可以是不确定的,并且您可以具有竞争条件,而现实世界中的输入也可以是不确定的。

–rackandboneman
17年3月31日在14:28

如果他们无法解释问题的发生方式,那么他们需要改进其跟踪/调试功能。

–凯文·麦坚时(Kevin McKenzie)
17年3月31日在18:27

#3 楼

我喜欢其他答案,但我想添加自动化功能。


我无法编写自动化测试,因为这是一个复杂的场景。


如果可以手动(在计算机上)进行操作,则可以将其自动化,但是不必为此创建可维护的自动化测试。我希望大多数(即使不是全部)方案都可以使用记录和回放工具进行循环。问题是随机发生的。

我会尝试确保问题至少在X次或循环之后发生。这样,开发人员便知道运行自动化测试以验证该问题是否已解决的时间。随机缺陷。

解决问题后,我将测试循环几天以进行进一步确认。

仍然,进行根本原因分析是明智的,考虑其他地点是否可能有类似问题,并加以解决。没有什么比将其固定在一个位置然后让您的客户开始抱怨另一个位置更糟糕了。

评论


它在哪里说测试方案不涉及实际/离线步骤?考虑一个很难自动打印和打印物理标签的生态系统:)考虑一个涉及生产系统的测试场景,在该生产系统中必须手动清理测试数据或失败的测试结果。考虑一下将软件在其他系统中启动交易(在最坏的情况下,进行银行真实交易)作为其测试的一部分...

–rackandboneman
17年3月31日14:33

@rackandboneman稍微更改了我的文字。是的,我错误地认为这是计算机上的一个进程。我还是想保留我的答案,以触发测试人员考虑自动化问题,并使每个自动化问题重复出现。甚至某些真正的手动过程也可以自动化。我已经看到模型火车可用于测试无线信用卡交易:)只是想一下就跳开思路。

– Niels van Reijmersdal
17年3月31日14:43在

#4 楼

这是几乎将犯罪用于统计的一个很好的例子。

让我想起了货运崇拜编码(https://en.wikipedia.org/wiki/Cargo_cult_programming)。

除非您的试验是随机的(即无意识的),但并非如此,否则使用统计推理几乎肯定是错误的。

数学必须遵循模型,并且您似乎对问题的模型没有很好的理解。 (如果您这样做了,则不会问您的问题)。显而易见的答案是beta测试。假设您想知道在Beta测试之前需要进行多少测试,那么答案是您需要进行“足够”的测试,以便您确信发生的频率大大降低了(基本上消失了)。

鉴于随机噪声通常以√n缩放,因此您必须进行大约10次(随机)试验才能确定错误率不是20%(或更高),然后执行100次坦率地说,如果您不尝试使用一定数量(多少个IDK,可能是10或20个)机器/网络配置(可以用来证明该错误发生在旧代码中)(至少是20个),或每份重复50次,我对它已被修复的说法不太满意。同样,如果没有良好的问题模型,您对问题已解决的任何信心大多只是一厢情愿的想法。抱歉。除了最简单的代码外,我们缺乏可靠地确定可靠性的能力。

我看到的其他答案都假设是纯剪切和粘贴的情况,其中“错误代码”被切掉并替换为“良好代码”。那几乎永远不会发生。修补程序通常解决多个(通常是相互关联的)问题。仅限于一行源代码的错误通常不会引起“罕见”的偶然错误。最后一条评论。我从不雇用相信20%的频率比率是一个罕见问题的程序员。假设您每年有20%的朋友死亡。罕见?不!当然,这是有争议的,但是我的稀有概念是千分之一或更少,而不是20%。

#5 楼

经验告诉我,在这种情况下,环境是必不可少的。
您需要了解修复程序,开发人员要解决什么问题。
例如,开发人员可能只是简化了代码的限制。
或更具有防御性-例如如果出现意外输入,则在流程中更早返回。如果是这种情况,请他给您提供一个没有修复的版本,但要在他放置防护罩的区域记录日志。
在修复之前和之后仔细检查日志。多少测试就足够了。

#6 楼

我不知道您是在说纯软件系统,还是处理电子和传感器输入的系统,但是无论哪种方式,答案都是单元测试和白盒测试。您的故障模式要么发生在预期的输入内,要么发生在外部。设计运行。超出边界条件的输入应通过验证进行处理。那可能就是解决方法,也可能指向某些上游设备或数据未在其设计规格内输出数据。不管哪种方式,您都想验证代码上的输入。 >一旦重现了发生故障的条件的组合(并且可能不止一个),则可以通过对代码进行白盒检查来确定这些条件是否在原始代码将失败的情况下提供了输入,并且您的修复有效。如果您的修复解决了单元测试中发现的所有故障模式,则说明它是合理有效的。如果不能解决所有故障模式,则还有更多工作要做。

#7 楼

我正在开发基于Windows的应用程序,根据我的经验,我多次遇到这种情况。对于一些错误,有些时间的模拟是中等的,而有时则很低。 (在提供bug演示之后),一旦解决,就向他(开发人员)询问解决方案,然后执行复制(模拟)步骤几次,并执行一些与最新修复相关的方案。

让我们考虑以下示例,
在测试一个视频监视应用程序时,我遇到了一次崩溃。它在模拟用户何时尝试收听特定网络摄像头的实时音频。但是模拟非常罕见。我以某种方式将问题演示给了一位具有正确堆栈跟踪的开发人员。我们试图通过堆栈跟踪来获得准确的模拟,但是我们没有这样做,因为模拟非常罕见。因此最后通过堆栈跟踪,开发人员了解了问题和原因与音频设备的启动状态有关。因此,他在启动和停止音频设备时应用了一些锁定。了解了解决方案后,我剩下了一些场景来测试在添加,删除,启动和停止网络摄像头时应用程序是否挂起。