Как ждать кеширования Redis для кеширования информации - PullRequest
0 голосов
/ 25 марта 2019

Я использую spring-data-redis и пытаюсь создать джунит, с помощью которого я могу проверить свою логику кэширования.Тестовый случай спорадически работает.Я предполагаю, что если логика кэширования завершается до вызова второго вызова метода, то она работает, иначе она не работаетЕсли некоторые сталкивались с подобной проблемой, я хотел бы понять, как они заставили это работать.На данный момент я использую 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());
}

Ответы [ 2 ]

0 голосов
/ 28 марта 2019

Фактическая проблема не связана со временем ожидания потока.Для работы кеша 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());
 }
0 голосов
/ 26 марта 2019

Проблемы во время ожидания в течение короткого промежутка времени, что очень часто встречается в распределенной системе.Чтобы избавиться от необходимости ждать слишком долго для тестового утверждения, есть небольшой инструмент под названием 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), вы можете запустить несколько первых запросов к нему или дождаться определенного условия , прежде чем начинать с вашеготесты.

...