【问题标题】:How to wait for Redis cache to cache the information如何等待Redis缓存缓存信息
【发布时间】:2019-08-16 01:36:29
【问题描述】:

我正在使用 spring-data-redis 并尝试使用 junit 来测试我的缓存逻辑。测试用例偶尔会起作用。我猜如果缓存逻辑在调用第二个方法调用之前完成,那么它会起作用,否则它会失败。如果有些人遇到过类似的问题,我想了解他们是如何做到的。截至目前,我正在使用 thread.sleep() 但正在寻找替代方案。

  @Test
  public void getUserById() {
  User user = new User("name", "1234");
when(userRepository.findbyId("1234")).thenReturn(Optional.ofNullable(user));
  // first method call
  User user1 = userService.findbyId("1234");

  assertThat(user.getName()).isEqualTo(user1.getName());
  assertThat(user.getId).isEqualTo(user1.getId());

  // sleeping the thread so to provide caching aspect sufficient time 
  // to cache the information
  try {
    Thread.sleep(1000);
  } catch (InterruptedException e) {
    e.printStackTrace();
  }
  // second method call, expecting cache to work.
  userCache = userService.findbyId("1234");
  verify(userRepository, never()).findbyId("1234");
  assertThat(user.getName()).isEqualTo(userCache.getName());
  assertThat(user.getId).isEqualTo(userCache.getId());
}

【问题讨论】:

    标签: java spring redis spring-data spring-cache


    【解决方案1】:

    实际问题不在于线程等待时间。要使 Redis 缓存工作,需要跨越一个单独的线程。对于我的服务测试,我通过一个单独的测试用例对其进行了测试。

     @Test
     public void getUserById() {
       User user = new User("name", "1234");
       when(userRepository.findbyId("1234")).thenReturn(Optional.ofNullable(user));
        // first method call
       User user1 = userService.findbyId("1234");
       assertThat(user.getName()).isEqualTo(user1.getName());
       assertThat(user.getId).isEqualTo(user1.getId());
     }
     //ensure this test case is executed after getUserById. I used 
     //@FixMethodOrder(MethodSorters.NAME_ASCENDING)
     @Test
     public void getUserById_cache() {
       User user1 = userService.findbyId("1234");
       Mockito.verify(userRepository, never()).findbyId("1234")
       assertThat(user.getName()).isEqualTo(user1.getName());
       assertThat(user.getId).isEqualTo(user1.getId());
     }
    

    【讨论】:

      【解决方案2】:

      等待很短时间的运行时问题在分布式系统中很常见。为了解决等待测试断言过长的需要,有一个名为Awaitility 的小工具。

      有了这个,你基本上可以通过多次查询断言来做一个更聪明的等待,在一定的时间间隔内,直到达到给定的超时(……等等)。

      关于你的例子,试试这个:

              Awaitility.await()
                      .pollInterval(new Duration(1, TimeUnit.SECONDS))
                      .atMost(new Duration(10, TimeUnit.SECONDS))
                      .untilAsserted(() -> 
                          User user1 = userService.findbyId("1234");
                          assertThat(user1.getName()).isEqualTo(user.getName());
      
      

      关于您问题的另一部分,在集成测试中,您实际上可以对您的 Redis 实例执行某种预热,或者如果您有容器化集成测试(例如 Docker),您可以在其上触发一些第一个请求,或者wait for a certain condition 在开始测试之前。

      【讨论】:

        猜你喜欢
        • 2015-11-27
        • 1970-01-01
        • 2016-03-29
        • 2014-05-14
        • 2018-02-14
        • 2014-05-01
        • 1970-01-01
        • 2018-01-30
        相关资源
        最近更新 更多