Develop short video e-commerce unit test from scratch (TestNG)

Introduction

Official website : https://testng.org/doc/index.html

TestNG is a Java-based open source testing framework. The framework is inspired by JUnit and NUnit, but introduces some new features to make it more powerful and easier to use. You can create HTML reports during test implementation. It has features like grouping tests, annotations, parameterization, etc. which help to create tests faster.

Core Features of TestNG

  • Run tests in a thread pool of any size, with various strategies available (all methods in their own thread, one thread per test class, etc.).

  • Test that your code is thread safe.

  • Flexible test configuration.

  • Support for data-driven testing (use @DataProvider).

  • Support parameters.

  • Powerful execution model (not anymore TestSuite).

  • Supported by multiple tools and plugins (Eclipse, IDEA, Maven, etc.).

  • Embeds BeanShell for flexibility.

  • Default JDK functions for runtime and logging (no dependencies).

  • Related methods for application server testing.

  • Unit testing, functional testing, end-to-end testing, integration testing, etc. can be done.

simple example

1. Add dependencies

        <dependency>
            <groupId>org.testng</groupId>
            <artifactId>testng</artifactId>
            <version>7.1.0</version>
            <scope>test</scope>
        </dependency>

TestNG up to v7.5: JDK 8 or later.

TestNG v7.6.0 and later: JDK 11 or later.

2. Simple test example

import org.testng.annotations.*;
 
public class SimpleTest {
    
    
 
 @BeforeClass
 public void setUp() {
    
    
   // 实例化此测试时将调用的代码
 }
 
 @Test(groups = {
    
     "fast" })
 public void aFastTest() {
    
    
   System.out.println("Fast test");
 }
 
 @Test(groups = {
    
     "slow" })
 public void aSlowTest() {
    
    
    System.out.println("Slow test");
 }
 
}
  • A test method can belong to one or more groups.

Execute tests and view test reports

Method 1 Run the testng.xml file in IDEA

Here is a testNG.xml file

<!DOCTYPE suite SYSTEM "https://testng.org/testng-1.0.dtd" >
<suite name="Suite1" verbose="1">
    <!-- 指定包名-->
    <test name="Regression1">
        <packages>
            <package name="test.sample"/>
        </packages>
    </test>

    <!-- 指定类名称 -->
    <test name="Regression2">
        <classes>
            <class name="test.sample.ParameterSample"/>
            <class name="test.sample.ParameterTest"/>
        </classes>
    </test>

    <!-- 指定要包含和排除的组和方法 -->
    <test name="Regression3">
        <groups>
            <run>
                <exclude name="brokenTests"/>
                <include name="checkinTests"/>
            </run>
        </groups>

        <classes>
            <class name="test.IndividualMethodsTest">
                <methods>
                    <include name="testMethod"/>
                </methods>
            </class>
        </classes>
    </test>

    <!-- 在属性中指定其他详细信息,例如是否并行运行测试、使用多少个线程、是否正在运行 JUnit 测试等 -->
    <test name="Regression4" preserve-order="false" parallel="methods" thread-count="5">
        <classes>
            <class name="test.Test1">
                <methods>
                    <include name="m1"/>
                    <include name="m2"/>
                </methods>
            </class>
            <class name="test.Test2"/>
        </classes>
    </test>

</suite>

Right click on the testNG.xml file to run it.

Method 2: Run the test class or package in IDEA

Right-click on the test class or test package to run it.

Way 3 Run tests in Maven

In the Maven project, Maven Surefire Pluginplug-ins are used to execute unit tests, so plug-ins need to be added to the pom.xml file Maven Surefire Plugin, and the test files to be executed can be configured in the configuration.

<build>
    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-surefire-plugin</artifactId>
            <!--<version>3.0.0-M5</version>-->
            <version>${maven-surefire-plugin.version}</version>
            <configuration>
                <trimStackTrace>true</trimStackTrace>
                <includes>
                    <include>**/*Test.java</include>
                    <include>**/*Tests.java</include>
                </includes>
                <excludes>
                    <exclude>**/integration/**</exclude>
                </excludes>
                <parallel>classes</parallel>
                <threadCountMethods>2</threadCountMethods>
                <useSystemClassLoader>false</useSystemClassLoader>
                <forkCount>1</forkCount>
                <reuseForks>true</reuseForks>
                <argLine>-Xmx1024m -XX:MaxPermSize=256m</argLine>
                <rerunFailingTestsCount>3</rerunFailingTestsCount>
                <testFailureIgnore>true</testFailureIgnore>
                <reportFormat>plain</reportFormat>
                <reportsDirectory>${project.build.directory}/surefire-reports</reportsDirectory>
            </configuration>
        </plugin>
    </plugins>
</build>

After execution, the surefire report will be stored in the target/surefire-reports folder by default.

  • <trimStackTrace>Set to trueto crop stack trace information to make it more readable.
  • <parallel>Set to classes, to allow parallel execution of test classes, improving execution speed.
  • <threadCountMethods>Set to an appropriate number of threads for parallel execution of test methods.
  • <useSystemClassLoader>Set to false, to avoid using the system classloader, reducing possible conflicts.
  • <forkCount>Set to 1to avoid using multiple processes to execute tests.
  • <reuseForks>Set to true, to reuse the test process and improve execution efficiency.
  • <argLine>Additional JVM parameters can be specified, such as heap memory size, permanent generation size, etc.
  • <rerunFailingTestsCount>Set to an appropriate value to rerun tests if they fail.
  • <testFailureIgnore>Set to trueto ignore test failures and continue the build process.
  • <reportsDirectory>Specifies the output directory for test reports.

Maven also has some common commands of its own, and we can execute test codes through Maven commands.

编译:mvn compile  --src/main/java目录java源码编译生成class (target目录下)
测试:mvn test    --src/test/java 目录编译
清理:mvn clean    --删除target目录,也就是将class文件等删除
打包:mvn package  --生成压缩文件:java项目#jar包;web项目#war包,也是放在target目录下
安装:mvn install   --将压缩文件(jar或者war)上传到本地仓库
部署:mvn deploy     --将压缩文件上传私服

​ We can mvn clean testexecute the test case by calling the plug-in in pom.xml Maven Surefire Plugin-> run the configured test case.

skip test

  • mvn clean package/install -DskipTests

  • mvn clean package/install -Dmaven.test.skip=true

Statistical Test Coverage

The higher the test code coverage, the higher the code quality

Method 1 IDEA supports detailed code test coverage statistics

It's very simple not to introduce

Method 2: Maven supports test coverage

JaCoCo is an open source coverage tool. Its development language is java. Its usage method is very flexible and can be embedded in Ant and Maven. Many third-party tools provide JaCoCo integration, such as sonar and Jenkins.

JaCoCo includes coverage counters of various scales, including instruction-level coverage (Instructions, C0coverage), branches (Branches, C1coverage), cyclomatic complexity (CyclomaticComplexity), line coverage (Lines), method coverage (non-abstract methods), Class coverage (classes)

pom.xml add

   <!-- jacoco: generate test coverage report -->
        <jacoco.version>0.8.8</jacoco.version>
            <plugin>
                <groupId>org.jacoco</groupId>
                <artifactId>jacoco-maven-plugin</artifactId>
                <version>${jacoco.version}</version>
                <configuration>
                    <includes>
                        <include>com/**/*</include>
                        <include>**/*Test.java</include>
                    </includes>
                    <excludes>
                        <exclude>**/AccountImageUtilTest.java</exclude>
                    </excludes>
                    <skip>false</skip>
                </configuration>
                <executions>
                    <execution>
                        <goals>
                            <goal>prepare-agent</goal>
                        </goals>
                    </execution>
                    <execution>
                        <id>generate-code-coverage-report</id>
                        <phase>test</phase>
                        <goals>
                            <goal>report</goal>
                        </goals>
                    </execution>
                </executions>
            </plugin>

Execute in the root directory of the project mvn clean testto execute the unit test and generate a coverage report. After the report is generated ./target/site/jacoco/index.html, open the file through a browser, and you can see the overall coverage and unit test status.

Create test cases in IDEA

Use IDEA to quickly create unit tests to improve development and testing efficiency

Use on the name of the class or interface (recommended to create based on the interface) that needs to be tested Alt+Enter, and then select Create Test .

Common Notes

annotation note
@BeforeSuite The annotated method will be run before the entire test suite
@AfterSuite The annotated method will be run after the entire test suite
@BeforeTest The annotated method will be run before all test cases in the test suite are executed
@AfterTest The annotated method will be run after all test cases in the test suite are executed
@BeforeGroups The annotated method will be run before any use cases in the specified group are executed
@AfterGroups The annotated method will run after any use case in the specified group is executed
@BeforeClass Annotated methods will run before calling the first test method in the current class .
@AfterClass Annotated methods will run after all test methods in the current class have run .
@BeforeMethod Annotated methods will be run before every test method .
@AfterMethod Annotated methods will be run after each test method .
@DataProvider The annotated method is forced to return a two-dimensional array Object[ ][ ] as a data factory for another @Test method
@Factory The annotated method, as an object factory, is forced to return an object array Object[]
@Listeners Define a listener for the test class
@Parameters Define a set of parameters, pass the value of the parameter to the method during the running of the method, and the value of the parameter is defined in testng.xml
@Test The marked method is a test method. If the mark is a class, all public methods in this class are test methods

The specific life cycle is as follows :

img

Common scene

ignore test

Sometimes, you may need to temporarily ignore certain test methods to avoid executing them. You can use @Test(enabled = false)annotations to mark test methods that need to be ignored.

import org.testng.annotations.Test;

public class IgnoreTest {
    
    

  @Test
  public void testMethod1() {
    
    
    // 测试方法1的代码
  }

  @Test(enabled = false)
  public void testMethod2() {
    
    
    // 测试方法2的代码
  }
}

testMethod2is marked as enabled = false, indicating that the test method will be ignored and will not be executed. Only test methods marked with enabled = trueor without enabledthe attribute will be executed.

parametric test

With parameterized testing, you can run the same test method with different input values ​​to verify how your code behaves under different parameters.

import org.testng.annotations.DataProvider;
import org.testng.annotations.Test;
import static org.testng.Assert.*;

public class ParameterizedTest {
    
    

  @DataProvider(name = "additionData")
  public Object[][] additionData() {
    
    
    return new Object[][] {
    
    
      {
    
    2, 3, 5},
      {
    
    5, 5, 10},
      {
    
    -10, 10, 0}
    };
  }

  @Test(dataProvider = "additionData")
  public void testAddition(int a, int b, int expected) {
    
    
    int result = Calculator.add(a, b);
    assertEquals(result, expected);
  }
}

test group

With Test Groups, you can categorize test methods and selectively run specific groups of tests.

import org.testng.annotations.Test;
import static org.testng.Assert.*;

public class GroupTest {
    
    

  @Test(groups = "smoke")
  public void testLogin() {
    
    
    // 测试登录功能
    assertTrue(true);
  }

  @Test(groups = "regression")
  public void testHomePage() {
    
    
    // 测试首页功能
    assertTrue(true);
  }

  @Test(groups = "regression")
  public void testProfilePage() {
    
    
    // 测试个人资料页面功能
    assertTrue(true);
  }
}

exception test

Verify that the code correctly throws the expected exceptions in the test.

import org.testng.annotations.Test;

public class ExceptionTest {
    
    

  @Test(expectedExceptions = ArithmeticException.class)
  public void testDivideByZero() {
    
    
    int result = Calculator.divide(10, 0);
  }
}

The expected exception type is specified using @Testthe annotation's attribute. expectedExceptionsIf the code executed in the test method does throw the specified exception, the test will be marked as passed.

timeout test

Set the maximum execution time of the test method to ensure that the code completes execution within the specified time frame.

import org.testng.annotations.Test;

public class TimeoutTest {
    
    

  @Test(timeOut = 500)
  public void testLongRunningOperation() throws InterruptedException {
    
    
    // 模拟一个长时间运行的操作
    Thread.sleep(1000);
  }
}

The maximum execution time in milliseconds is specified using the @Testannotated attribute. timeOutIf the execution time of the test method exceeds the specified time, the test will be marked as failed.

multithreaded test

Using TestNG, you can execute test methods concurrently in multiple threads to simulate concurrency and parallel scenarios. This can be achieved by @Testsetting the threadPoolSizeand invocationCountattributes in the annotation.

import org.testng.annotations.Test;

public class MultiThreadTest {
    
    

  @Test(threadPoolSize = 5, invocationCount = 10)
  public void testMethod() {
    
    
    // 在多个线程中并发执行的测试方法
  }
}

testMethodUsing threadPoolSize = 5and invocationCount = 10means that the test method will be executed concurrently in a thread pool with 5 threads, for a total of 10 executions. This allows you to simulate concurrent scenarios and observe how your test methods behave in a multi-threaded environment.

Note: When writing multi-threaded tests, make sure the test methods are thread-safe, and handle synchronization between threads and access to shared resources.

rerun failed tests

When executing tests in a maven environment, TestNG will create a file named in the output directory every time a test fails testng-failed.xml. This XML file contains the information needed to rerun only those failed methods, enabling you to quickly reproduce failures without running the entire test.

\target\surefire-reports\testng-failed.xml

Affirmation

In TestNG, commonly used assertion methods are located org.testng.Assertin the class, which provides a series of assertion methods for verifying test results. The following are code examples of some commonly used assertion methods and their best practices:

Verify that two values ​​are equal

assertEquals: Validates that two values ​​are equal.

import org.testng.Assert;
import org.testng.annotations.Test;

public class AssertionTest {
    
    

  @Test
  public void testAddition() {
    
    
    int result = Calculator.add(2, 3);
    Assert.assertEquals(result, 5, "Addition result is incorrect.");
  }
}

In the example above, assertEqualsthe method is used to verify resultthat the value of is equal to 5. If the assertion fails, an AssertionError is thrown with the specified error message.

Verify if a condition is true or false

assertTrueAND assertFalse: Validates whether a condition is true or false.

import org.testng.Assert;
import org.testng.annotations.Test;

public class AssertionTest {
    
    

  @Test
  public void testIsEvenNumber() {
    
    
    int number = 10;
    Assert.assertTrue(number % 2 == 0, "Number is not even.");
  }
}

In the example above, assertTruethe method is used to verify numberthat is even. If the condition is not met, the assertion fails with an error message.

Validates whether a value is null or not null

assertNullAND assertNotNull: Validates whether the value is null or not null.

import org.testng.Assert;
import org.testng.annotations.Test;

public class AssertionTest {
    
    

  @Test
  public void testArray() {
    
    
    String[] names = {
    
    "John", "Jane", "Doe"};
    Assert.assertNotNull(names, "Array is null.");
  }
}

In the above example, assertNotNullthe method is used to verify namesthat the array is not null. If the array is null, the assertion fails with an error message.

Verify that the expected exception was thrown

assertThrows: Verify that the expected exception was thrown.

import org.testng.Assert;
import org.testng.annotations.Test;

public class AssertionTest {
    
    

  @Test
  public void testDivideByZero() {
    
    
    Assert.assertThrows(ArithmeticException.class, () -> Calculator.divide(10, 0));
  }
}

In the above example, assertThrowsthe method is used to verify Calculator.divide(10, 0)that the exception was thrown ArithmeticException. If the expected exception is not thrown, the assertion fails.

Guess you like

Origin blog.csdn.net/abu935009066/article/details/131797266