当前位置: 首页 > 知识库问答 >
问题:

我无法将Mockito单元测试改写为Spock规范

左丘成业
2023-03-14
@Service
public class UserDetailsServiceImpl implements UserDetailsService {

    private final UserRepository userRepository;

    @Autowired
    public UserDetailsServiceImpl(UserRepository userRepository) {
        this.userRepository = userRepository;
    }

    @Override
    public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
        final UserEntity user = userRepository.findByUsername(username);

        if (user == null) {
            throw new UsernameNotFoundException("Cannot find user with username " + username);
        }

        return new User(user);
    }
}

并且我使用JUnit和Mockito为该方法编写了一个单元测试。这些测试正在工作:

@RunWith(SpringRunner.class)
@DirtiesContext
public class UserDetailsServiceTest {

    @Autowired
    private UserDetailsService userDetailsService;

    @Test
    public void shouldFindUser() throws Exception {
        // given
        final UserEntity user = new UserEntity(
                1L,
                "username",
                "username@email.com",
                "password",
                new ArrayList<>() // list of roles
        );

        when(UserDetailsServiceTestContext.userRepository.findByUsername(user.getUsername()))
                .thenReturn(user);

        // when
        final UserDetails result = userDetailsService.loadUserByUsername(user.getUsername());

        // then
        assertThat(result).isEqualTo(UserFactory.create(user));
        verify(UserDetailsServiceTestContext.userRepository)
                .findByUsername(user.getUsername());
    }

    @Test(expected = UsernameNotFoundException.class)
    public void shouldNotFindUser() throws Exception {
        // given
        when(UserDetailsServiceTestContext.userRepository.findByUsername(anyString()))
                .thenReturn(null);

        // when
        final UserDetails result = userDetailsService.loadUserByUsername(new String());
    }

    @TestConfiguration
    static class UserDetailsServiceTestContext {

        @MockBean
        private static UserRepository userRepository;

        @Bean
        UserDetailsService userDetailsService() {
            return new UserDetailsServiceImpl(userRepository);
        }
    }

}

现在我尝试使用Groovy和Spock框架编写这些测试。我写了如下规范:

def 'should find user'() {
        given:
            def user = new UserEntity(
                1L,
                "username",
                "username@email.com",
                "password"
                new ArrayList<>() // list of roles
            )

            userRepository.findByUsername(user.username) >> user
            // userRepository.findByUsername(_ as String) >> user // also working

        when:
            def result = userDetailsService.loadUserByUsername(user.username)

        then:
            result == new User(user)
    }

这个测试起作用了。但是,当我想通过在节中添加验证userRepository的调用时:语句1*userRepository.findByUserName(user.userName)1*userRepository.findByUserName(_as String)我得到一个错误UserDetailsServiceSpec.should find user并返回新用户:36?UserNameNotFound。第36行位于节中,此时:

共有1个答案

水渊
2023-03-14

您需要在一个步骤中完成剪切和验证

then:
1 * userRepository.findByUsername(user.username) >> user

关于细节,这里是我从Spock中预定义的模拟响应中得到的答案:

请参阅文档

setup:
subscriber.receive("message1") >> "ok"

when:
publisher.send("message1")

then:
1 * subscriber.receive("message1")
 类似资料:
  • 我在java中使用mockito编写单元测试。 这就是我要测试的声明。 电影是电影名称的集合,是识别电影的关键。 我嘲笑了守望者班 Mockito.when(watcher.watch(Matchers.any(Set.class))) “thenReturn”中包括什么??

  • 问题内容: 我正在使用RestTemplate 方法将正文发布到端点。我需要使用Mockito为我的代码编写测试用例的帮助。返回类型为void,但是可以将其更改为,或者需要进行测试。我已经提到了许多其他文档,但是它们非常笼统,我尝试使用它们,但是由于and和return类型是不同的,所以大多数对我来说都不起作用。。任何建议表示赞赏。谢谢 这是我的Java课 问题答案: 您正在测试MyClass类中

  • 非常感谢您的任何建议,

  • 为什么在STS中运行单元测试是有效的,而在bash中运行mvn测试会产生错误。Groovy库位于类路径中。我也很好奇mvn测试与spock测试有何不同。mvn测试不能拿起斯波克测试吗? pom.xml

  • 我不会告诉你有关后台任务的单元测试的任何内容,因为Hangfire没有添加任何特定方法 (除了 IJobCancellationToken 接口参数)去改变任务。使用您最喜爱的工具,并照常写入单元测试。本节介绍如何测试创建的后台任务。 所有的代码示例都使用静态 BackgroundJob 类来告诉你如何做这个或那些东西,只是出于简单演示的目的。但是当你想测试调用的静态方法时,会变得很痛苦。 不用担