”工欲善其事,必先利其器。“—孔子《论语.录灵公》
首页 > 编程 > 使用 Java 的 carlspring/idempotence 框架编写可并行测试

使用 Java 的 carlspring/idempotence 框架编写可并行测试

发布于2024-11-08
浏览:794

Writing parallelizable tests with the carlspring/idempotence framework for Java

免责声明

这是我在 Medium.com 上文章的重新发布,希望作为 #Hacktoberfest 的一部分接触到更多 OSS 开发人员。

介绍

您是否曾经不得不处理一些片状并行测试,这些测试大部分时间都能通过,但随后突然开始因不一致的随机错误而失败?您是否曾经不得不修复共享相同资源文件的测试并并行修改它们,以使您和其他测试的结果感到困惑?您是否花了无数个夜晚尝试重构此类代码,使其能够正确并行化并获得可重现且有保证的结果?

这是一个复杂的主题,并不总是可以直接解决,特别是在现有的大型代码库中。然而,遵循一组简单的规则可以帮助您实现这一目标,而 carlspring/idempotence 框架旨在帮助您实现这一点。

什么是测试隔离?

为了使测试始终可重现,您需要确保它们的资源文件仅包含并隔离给它们。这意味着每个测试都应该独占其测试资源,其他测试不应修改它们。

什么是测试幂等性?

测试幂等性意味着您的测试将始终返回相同的结果。无论它们被执行了多少次,也无论并行运行什么其他测试。

Java 的 carlspring/idempotence 框架是什么

这是一个轻量级框架,有助于以隔离的方式为 JUnit5 测试定义和复制测试资源文件。测试资源通过注解的方式定义,并复制到各自的目录中,以帮助实现测试资源分离和隔离。

Java carlspring/幂等框架如何工作

所有常用的测试资源照常存放在 src/test/resources 目录下。然后,每个测试方法使用 @TestResources 注释定义它所需的资源。该框架将这些资源复制到每个测试方法的独立目录中。这确保了它能够独占访问所需的资源,从而防止并行运行的其他测试(包括同一测试类中的其他测试方法)的干扰。

对于每个构建工具,都有一个单独的依赖项,其中包含该工具的特定目录布局的路径相关转换逻辑。 (作为一个非常简单的例子,Maven 将构建的代码放在目标下,而 Gradle 使用构建来实现此目的;资源的放置方式不同,等等)。下面将对此进行更多解释。

如何使用 Java carlspring/idempotence 框架编写测试

以下是您需要开始的步骤。

定义依赖关系

您需要为构建工具定义相应的依赖项。您可以在此处查看最新发布的版本。

  • 对于 Gradle(使用 Groovy DSL):

testImplementation "org.carlspring.testing.idempotence:idempotence-gradle:1.0.0-rc-3"


  • Gradle(使用 Kotlin DSL):

testImplementation("org.carlspring.testing.idempotence:idempotence-gradle:1.0.0-rc-3")


  • 对于 Maven:


    org.carlspring.testing.idempotence
    idempotence-maven
    1.0.0-rc-3
    test



添加注释

您的测试类必须使用 @ExtendWith(TestResourceExtension.class) 注释进行注释。该注释负责资源的实际复制。

您还需要使用@TestResources注释来注释您的测试方法,以指定它们需要的资源。

例如:


package com.foo;

import org.carlspring.testing.idempotence.annotation.TestResource;
import org.carlspring.testing.idempotence.annotation.TestResources;
import org.carlspring.testing.idempotence.extension.TestResourceExtension;

@ExtendWith(TestResourceExtension.class)
class MyTest {

    @Test
    @TestResources({ @TestResource(source = "classpath:/foo.txt"),
                     @TestResource(source = "classpath*:/**/bar.txt")} )
    void testFoo()
    {
        // Perform whatever checks you need using these resources
    }

}


对于每种测试方法,将使用以下格式创建一个目录:

  • 对于 Gradle 项目,有一个名为 MyTest 的测试,其方法为 testFoo, 它们将被放置在:

build/test-resources/MyTest-testFoo/nested/dir/foo.txt
build/test-resources/MyTest-testFoo/bar.txt


  • 对于 Maven 项目,有一个名为 MyTest 的测试,其方法为 testFoo, 它们将被放置在:

target/test-resources/MyTest-testFoo/nested/dir/foo.txt
target/test-resources/MyTest-testFoo/bar.txt


这样您的测试将把它们需要的资源复制到它们自己的独立目录中。此时,您可以从它们所属的测试方法中修改这些测试资源,并且您的结果应该是幂等的,前提是它们仅依赖于基于文件的资源而不依赖于其他类型的共享资源(数据库、第三方服务等)。

在哪里可以找到文档

幂等项目的文档可以在这里找到。

您可以查看概念概述,以获取有关工作原理的更详细说明。

如何贡献

这是一个全新项目,核心功能和基础设施已就位,但始终欢迎帮助。

具有 JUnit、Springframework、MkDocs 经验的贡献者可以通过一些出色的想法和解决方案帮助塑造项目。也非常欢迎能够提供反馈的尝鲜者!

标记为 hacktoberfest 或需要帮助的问题可供争夺,应该可以帮助您快速入门。你可以在这里找到它们。

结论

编写测试用例时最重要的事情之一是测试将使用的测试数据并在运行之间保持理智。通过遵循一组简单的规则来保持测试之间的数据隔离,您可以实现结果的幂等性和可靠性。

carlspring/idempotence 项目提供了易于使用的框架,适用于新建项目和重构遗留项目。

版本声明 本文转载于:https://dev.to/carlspring/writing-parallelizable-tests-with-the-carlspringidempotence-framework-for-java-420n?1如有侵犯,请联系[email protected]删除
最新教程 更多>
  • 如何限制动态大小的父元素中元素的滚动范围?
    如何限制动态大小的父元素中元素的滚动范围?
    在交互式接口中实现垂直滚动元素的CSS高度限制问题:考虑一个布局,其中我们具有与用户垂直滚动一起移动的可滚动地图div,同时与固定的固定sidebar保持一致。但是,地图的滚动无限期扩展,超过了视口的高度,阻止用户访问页面页脚。$("#map").css({ marginT...
    编程 发布于2025-04-17
  • 如何高效地在一个事务中插入数据到多个MySQL表?
    如何高效地在一个事务中插入数据到多个MySQL表?
    mySQL插入到多个表中,该数据可能会产生意外的结果。虽然似乎有多个查询可以解决问题,但将从用户表的自动信息ID与配置文件表的手动用户ID相关联提出了挑战。使用Transactions和last_insert_id() 插入用户(用户名,密码)值('test','test...
    编程 发布于2025-04-17
  • 使用jQuery如何有效修改":after"伪元素的CSS属性?
    使用jQuery如何有效修改":after"伪元素的CSS属性?
    在jquery中了解伪元素的限制:访问“ selector 尝试修改“:”选择器的CSS属性时,您可能会遇到困难。 This is because pseudo-elements are not part of the DOM (Document Object Model) and are th...
    编程 发布于2025-04-17
  • 如何使用Python理解有效地创建字典?
    如何使用Python理解有效地创建字典?
    在python中,词典综合提供了一种生成新词典的简洁方法。尽管它们与列表综合相似,但存在一些显着差异。与问题所暗示的不同,您无法为钥匙创建字典理解。您必须明确指定键和值。 For example:d = {n: n**2 for n in range(5)}This creates a dicti...
    编程 发布于2025-04-17
  • 如何正确使用与PDO参数的查询一样?
    如何正确使用与PDO参数的查询一样?
    在pdo 中使用类似QUERIES在PDO中的Queries时,您可能会遇到类似疑问中描述的问题:此查询也可能不会返回结果,即使$ var1和$ var2包含有效的搜索词。错误在于不正确包含%符号。通过将变量包含在$ params数组中的%符号中,您确保将%字符正确替换到查询中。没有此修改,PDO...
    编程 发布于2025-04-17
  • 如何使用Depimal.parse()中的指数表示法中的数字?
    如何使用Depimal.parse()中的指数表示法中的数字?
    在尝试使用Decimal.parse(“ 1.2345e-02”中的指数符号表示法表示的字符串时,您可能会遇到错误。这是因为默认解析方法无法识别指数符号。 成功解析这样的字符串,您需要明确指定它代表浮点数。您可以使用numbersTyles.Float样式进行此操作,如下所示:[&& && && ...
    编程 发布于2025-04-17
  • 解决MySQL错误1153:数据包超出'max_allowed_packet'限制
    解决MySQL错误1153:数据包超出'max_allowed_packet'限制
    mysql错误1153:故障排除比“ max_allowed_pa​​cket” bytes 更大的数据包,用于面对阴谋mysql错误1153,同时导入数据capase doft a Database dust?让我们深入研究罪魁祸首并探索解决方案以纠正此问题。理解错误此错误表明在导入过程中接...
    编程 发布于2025-04-17
  • 为什么我会收到MySQL错误#1089:错误的前缀密钥?
    为什么我会收到MySQL错误#1089:错误的前缀密钥?
    mySQL错误#1089:错误的前缀键错误descript [#1089-不正确的前缀键在尝试在表中创建一个prefix键时会出现。前缀键旨在索引字符串列的特定前缀长度长度,可以更快地搜索这些前缀。了解prefix keys `这将在整个Movie_ID列上创建标准主键。主密钥对于唯一识别...
    编程 发布于2025-04-17
  • 为什么Microsoft Visual C ++无法正确实现两台模板的实例?
    为什么Microsoft Visual C ++无法正确实现两台模板的实例?
    The Mystery of "Broken" Two-Phase Template Instantiation in Microsoft Visual C Problem Statement:Users commonly express concerns that Micro...
    编程 发布于2025-04-17
  • 如何在Java字符串中有效替换多个子字符串?
    如何在Java字符串中有效替换多个子字符串?
    在java 中有效地替换多个substring,需要在需要替换一个字符串中的多个substring的情况下,很容易求助于重复应用字符串的刺激力量。 However, this can be inefficient for large strings or when working with nu...
    编程 发布于2025-04-17
  • 如何修复\“常规错误:2006 MySQL Server在插入数据时已经消失\”?
    如何修复\“常规错误:2006 MySQL Server在插入数据时已经消失\”?
    How to Resolve "General error: 2006 MySQL server has gone away" While Inserting RecordsIntroduction:Inserting data into a MySQL database can...
    编程 发布于2025-04-17
  • 如何使用组在MySQL中旋转数据?
    如何使用组在MySQL中旋转数据?
    在关系数据库中使用mySQL组使用mySQL组进行查询结果,在关系数据库中使用MySQL组,转移数据的数据是指重新排列的行和列的重排以增强数据可视化。在这里,我们面对一个共同的挑战:使用组的组将数据从基于行的基于列的转换为基于列。 Let's consider the following ...
    编程 发布于2025-04-17
  • 哪种方法更有效地用于点 - 填点检测:射线跟踪或matplotlib \的路径contains_points?
    哪种方法更有效地用于点 - 填点检测:射线跟踪或matplotlib \的路径contains_points?
    在Python Matplotlib's path.contains_points FunctionMatplotlib's path.contains_points function employs a path object to represent the polygon.它...
    编程 发布于2025-04-17
  • 如何同步迭代并从PHP中的两个等级阵列打印值?
    如何同步迭代并从PHP中的两个等级阵列打印值?
    同步的迭代和打印值来自相同大小的两个数组使用两个数组相等大小的selectbox时,一个包含country代码的数组,另一个包含乡村代码,另一个包含其相应名称的数组,可能会因不当提供了exply for for for the uncore for the forsion for for ytry...
    编程 发布于2025-04-17
  • 如何使用node-mysql在单个查询中执行多个SQL语句?
    如何使用node-mysql在单个查询中执行多个SQL语句?
    Multi-Statement Query Support in Node-MySQLIn Node.js, the question arises when executing multiple SQL statements in a single query using the node-mys...
    编程 发布于2025-04-17

免责声明: 提供的所有资源部分来自互联网,如果有侵犯您的版权或其他权益,请说明详细缘由并提供版权或权益证明然后发到邮箱:[email protected] 我们会第一时间内为您处理。

Copyright© 2022 湘ICP备2022001581号-3