当前位置: 首页 > news >正文

北京网站设计建设如何做一个手机网站

北京网站设计建设,如何做一个手机网站,杭州建设网站职称人才工作专题,自做头像的网站前言 现在作者说明一下,作者需要开发一个简单的VueSpringboot前后端分离实验,想要尽量将测试的流程应用到这样的系统中。单元测试请见Junit单元测试_Joy T的博客-CSDN博客,而单元测试加上mock呢,最多也只能测试一下Service层的业…

前言 

现在作者说明一下,作者需要开发一个简单的Vue+Springboot前后端分离实验,想要尽量将测试的流程应用到这样的系统中。单元测试请见Junit单元测试_Joy T的博客-CSDN博客,而单元测试加上mock呢,最多也只能测试一下Service层的业务逻辑,对于数据访问层的代码,比如save/insert等等,用单元测试不是很到位。Junit+mock请见Mock简单应用_Joy T的博客-CSDN博客

首先因为这些数据访问层的层数几乎已经到底层,无法使用mock去模拟一个下层对象。其次,对于数据访问层,确实应该测试一下与数据库真实的连接了,这种接近于实际情况的交互还是使用集成测试会好一些。


集成测试与单元测试应用场景对比

对于何时应该进行单元测试和集成测试,确实存在一些争议和不同的做法。但大体上,以下是一个通常的建议和理由:

单元测试

  • 业务逻辑层(例如,服务层、工具类等):这是单元测试最有价值的地方。你可以测试逻辑是否正确、边界条件是否得到处理、异常是否正确抛出等。
  • 自定义工具或库:如果你开发了一些自定义的工具类或库函数,那么对它们进行单元测试是很有意义的。
  • 复杂的数据转换或处理:如果你的代码需要进行复杂的数据转换或处理(例如,将数据从一种格式转换为另一种格式),那么单元测试可以帮助确保这些转换或处理是正确的。

集成测试

  • 数据访问层(例如,使用MyBatis的Mapper):对于数据访问层,通常集成测试更有意义。你可能会想知道SQL查询是否正确、返回的数据是否符合预期、事务是否正确处理等。对于JavaWeb来说,数据访问层通常指Dao层;而对于Springboot来说,数据访问层就是Repository。
  • 外部服务交互:当你的代码与外部服务(例如,其他的微服务、第三方API等)交互时,集成测试可以帮助确保这些交互的正确性和稳定性。
  • 整体应用流程:测试应用的整体流程,确保各个组件、服务或模块之间的交互是正确的。

集成测试是不是就是接口测试?

  • 集成测试:它关注的是多个组件或系统的部分(如两个模块、一个服务和一个数据库等)如何一起工作。例如,你可能有一个测试来确保你的UserRepository能够正确地从数据库中检索数据。

  • 接口测试:接口测试或API测试,特指测试软件的接口,确保它们正常工作、可靠并且满足其预期的功能。这些接口可能是HTTP REST API、SOAP web服务或任何其他类型的API。

简言之,所有的接口测试都可以看作是集成测试,但并非所有的集成测试都是接口测试。集成测试包括的领域更大。


集成测试实例

在Spring Boot应用中,我们通常使用@DataJpaTest来进行数据访问层的集成测试。

UserRepository进行集成测试的示例

User.java (Entity)

@Entity
public class User {@Id@GeneratedValue(strategy = GenerationType.IDENTITY)private Long id;private String username;private String password;// getters, setters, constructors...
}

UserRepository.java

public interface UserRepository extends JpaRepository<User, Long> {Optional<User> findByUsername(String username);
}

UserRepositoryIntegrationTest.java (测试类)

@RunWith(SpringRunner.class)
@DataJpaTest
public class UserRepositoryIntegrationTest {@Autowiredprivate TestEntityManager entityManager;@Autowiredprivate UserRepository userRepository;@Testpublic void whenFindByUsername_thenReturnUser() {// givenUser john = new User("john", "123456");entityManager.persist(john);entityManager.flush();// whenOptional<User> found = userRepository.findByUsername(john.getUsername());// thenassertTrue(found.isPresent());assertEquals(found.get().getUsername(), john.getUsername());}// 其他相关的集成测试方法...
}
  • 我们使用@DataJpaTest启动一个嵌入式数据库,并自动配置Spring Data JPA
  • TestEntityManager提供了一种更为简单的方式来管理持久性上下文,并允许我们执行常见的数据库操作。

详解UserRepositoryIntegrationTest.java (测试类)

我们来逐步解释UserRepositoryIntegrationTest.java中的内容。

1. 基本设置

@RunWith(SpringRunner.class)
@DataJpaTest

@RunWith(SpringRunner.class):这个注解告诉JUnit使用Spring的测试运行器。这意味着我们可以在测试中利用Spring Boot的特性。

@DataJpaTest:这个注解专门为Spring Data JPA的测试提供支持。它会配置一个嵌入式数据库(默认是H2),并且会进行JPA的相关配置,使得我们可以直接测试与数据库的交互。这里的“集成”体现在我们实际与一个真实的数据库交互,而不是使用mock。

2. 属性和注入

@Autowired
private TestEntityManager entityManager;@Autowired
private UserRepository userRepository;

TestEntityManager:非常重要,这是专门为测试提供的实体管理器。它是JPA EntityManager的一个简化版本,用于数据库操作。我们可以使用它来添加、更新或删除测试数据。

UserRepository:这是我们要测试的Spring Data JPA repository。一个专门的固定的实体管理器,一个是我们要测试的Repository层。

3. 测试方法

@Test
public void whenFindByUsername_thenReturnUser() {// givenUser john = new User("john", "123456");entityManager.persist(john);entityManager.flush();// whenOptional<User> found = userRepository.findByUsername(john.getUsername());// thenassertTrue(found.isPresent());assertEquals(found.get().getUsername(), john.getUsername());
}

这个测试方法分为三个阶段:给定 (given),当 (when) 和那么 (then)。

  • 给定 (given): 这里,我们创建了一个新的用户对象,并使用TestEntityManager将其持久化到数据库中(persist&flush)。

  • 当 (when): 在这一步,我们试图通过UserRepositoryfindByUsername方法根据用户名找到用户。

  • 那么 (then): 这是我们的断言阶段,我们检查从UserRepository返回的值是否符合我们的预期。我们预期的是,当我们查询一个已经存在于数据库中的用户名时,UserRepository应该返回那个用户。

如果在这三个阶段中的任何一个阶段出现错误或异常,或者预期的结果与实际的结果不匹配,那么这个测试就会失败。


When 详解

 // when
Optional<User> found = userRepository.findByUsername(john.getUsername());

Optional是Java 8引入的一个容器对象它可能包含一个值,也可能不包含(即为空),就是表面意思:可选。其主要目的是提供一个明确的方式来处理null值的情况,避免NullPointerException,更加灵活,便于测试。

在我们讨论的上下文中,Optional存储的是单个User对象,不是数组,对象名为found。所以,found.get()返回的是单个User对象。

如果期望从数据库检索多个User对象,那么UserRepository的方法返回类型可能会是List<User>,而不是Optional<User>。例如:

List<User> findByUsername(String username);

在这种情况下,如果有多个与指定用户名匹配的用户,那么返回的列表将包含所有这些用户。你可以通过检查列表的大小或迭代列表中的每个用户来处理多个用户的情况。

但在大多数应用程序中,用户名通常是唯一的,所以通过用户名检索用户时,通常只返回一个用户。这也是为什么在很多情况下,你会看到Optional<User>作为返回类型。


Then 详解

    // thenassertTrue(found.isPresent());assertEquals(found.get().getUsername(), john.getUsername());

这两句代码是利用Java的Optional类以及JUnit的断言来验证测试的预期结果。这并不直接对应User类的方法,而是与UserRepository的方法以及Java的Optional类相关。

让我们详细分析:

assertTrue(found.isPresent());

这句代码使用的isPresent()方法是Optional类的方法。当我们使用Spring Data JPA的repository方法返回对象时,为了处理可能的null值(例如当对象不存在于数据库中时),通常会返回Optional<T>类型。Optional类有一个isPresent()方法,如果Optional内部包含一个非null值,它返回true,否则返回false,相当于isExist()

所以,assertTrue(found.isPresent());这行代码的意思是:我们期望UserRepository返回一个包含用户的Optional。

assertEquals(found.get().getUsername(), john.getUsername());

  • found.get(): 这是Optional类的另一个方法,它返回Optional对象内部的值(如果存在的话)。

  • getUsername(): 这是我们的User类的方法,用于获取用户的用户名。

所以,assertEquals(found.get().getUsername(), john.getUsername());这行代码的意思是:我们期望从数据库中检索到的用户(found.get())的用户名与我们原始存储的用户john的用户名相匹配。

这样,结合两句断言,我们可以测试UserReposiroty中定义的FindByUsername()方法是否能够按照用户名去得到指定用户!


SelectAll()!

当我们想测试类似selectAll这样的方法,返回的确实是一个List,一般不使用Optional类对象作为承载者。为了进行集成测试,我们可以添加一些记录到数据库,然后调用selectAll方法,最后验证返回的列表是否包含预期的记录。

以下是一个简单的示例,用于测试selectAll方法:

@RunWith(SpringRunner.class)
@DataJpaTest
public class UserRepositoryIntegrationTest {@Autowiredprivate TestEntityManager entityManager;@Autowiredprivate UserRepository userRepository;@Testpublic void testSelectAll() {// Given: 添加一些预期的记录到数据库User john = new User();john.setUsername("john");john.setPassword("john123");entityManager.persist(john);User jane = new User();jane.setUsername("jane");jane.setPassword("jane123");entityManager.persist(jane);// When: 调用selectAll方法List<User> users = userRepository.selectAll();// Then: 验证返回的列表是否包含预期的记录assertNotNull(users);assertTrue(users.size() >= 2);  // 因为你不确定测试数据库中是否有其他记录,所以我们检查是否至少有我们插入的记录// 更进一步的验证可以检查返回的用户是否真的是我们预期的那些用户assertTrue(users.stream().anyMatch(user -> user.getUsername().equals("john")));assertTrue(users.stream().anyMatch(user -> user.getUsername().equals("jane")));}
}

存储john&jane用户,调用selectAll()方法,使用断言验证selectAll查询到的信息有没有john&jane。

http://www.yayakq.cn/news/544017/

相关文章:

  • 关于建设学校网站策划书的范本厦门网站优化公司
  • 汕头市公司网站建设平台上海企业网站怎么建设
  • 网站建网站建站专业公司培训公司网站建设
  • 照片网站模板wordpress小视频主题
  • 同城网站开发徐州手机网站开发公司
  • 网站的首页文案app页面模板
  • 深圳优化公司踏高粱seo网站关键词优化排名技巧
  • 怎么做网站多少钱手机版网页制作
  • 网站建设导航分哪几类wordpress 检测404
  • 网站导航栏的设计与实现免费设计商标的网站
  • 成都科技网站建设费微网站是用什么开发的
  • 网站 网页设计php做不了大型网站吗
  • 鞍山做网站专业公司wordpress插件刷不出来
  • 网站建设与管理pdfpython编程语言大全
  • 专门做免费东西试吃的网站h5开发环境搭建
  • 免费做网站刮刮卡怎么写网站规划方案
  • glitch做网站网站优化公司怎么选
  • 设计师网站卡密登录电商网站开发设计方案
  • 酷站 网站模板建筑工程网络计划方法
  • 企业文化建设网站建设dede网站模板下载
  • 网站建设的公司系统规划方案盐城市建设局网站物业资质
  • 搭建网站钱虚拟主机建立网站
  • vue做的网站大全a市最牛的网站
  • 泉州网站设计找哪家兰溪优秀高端网站设计地址
  • 网站编程源码免费网站建设互诺科技
  • 做微博长图的网站如何设计大气的网站
  • 怎么做自己优惠券网站wordpress 转跳到登录
  • 有关房地产开发建设的网站怎么开通公司网站
  • 河南炒股配资网站开发兴平网站开发
  • 温州网络问政沈阳seo公司