Grails如何对异常执行单元测试

时间:2019-01-08 06:49:01

标签: unit-testing grails spring-security

我正在尝试测试帐户过期异常。

def authfail() {
    String msg = ''
    def exception = session[WebAttributes.AUTHENTICATION_EXCEPTION]

//        println("print exception: ${exception} | ${session} | ${springSecurityService.getCurrentUser()}")
    if (exception) {
        if (exception instanceof AccountExpiredException) {
            msg = message(code: 'springSecurity.errors.login.expired')
        }
        else if (exception instanceof CredentialsExpiredException) {
            msg = message(code: 'springSecurity.errors.login.passwordExpired')
        }
        else if (exception instanceof DisabledException) {
            msg = message(code: 'springSecurity.errors.login.disabled')
        }
        else {
            msg = message(code: 'springSecurity.errors.login.fail')
        }
    }

    if (springSecurityService.isAjax(request)) {
        render([error: msg] as JSON)
    }
    else {
        flash.message = msg
        redirect action: 'auth', params: params
    }
}

在不知如何触发过期的登录信息之前,我尝试编写上面的测试用例,因为我不知道如何触发过期的登录,这样才能满足抛出AccountExceptionExpired异常的单元测试条件。

void "test authFail"() {

when:
    session."${WebAttributes.AUTHENTICATION_EXCEPTION}" = new AccountExpiredException( 'This account has expired' )
    def logexp = controller.authfail()
then:
    logexp == 'springSecurity.errors.login.expired'
when:
    session."${WebAttributes.AUTHENTICATION_EXCEPTION}" = new CredentialsExpiredException( 'This credentials have expired' )
    def passexp = controller.authfail()
then:
    passexp == 'springSecurity.errors.login.passwordExpired'
when:
    session."${WebAttributes.AUTHENTICATION_EXCEPTION}" = new DisabledException( 'The account is disabled' )
    def logdis = controller.authfail()
then:
    logdis == 'springSecurity.errors.login.disabled'
when:
    session."${WebAttributes.AUTHENTICATION_EXCEPTION}" = new UnsupportedOperationException( 'Sorry, we were not able to find a user with that username and password.' )
    def logfail = controller.authfail()
then:
    logfail == 'springSecurity.errors.login.fail'
when:
    controller.authfail()
then:
    1 * springSecurityService.isAjax( _ ) >> true
    controller.response.json == [error :'springSecurity.errors.login.fail']

    }
}

2 个答案:

答案 0 :(得分:0)

以下内容将测试您的大部分方法:

curl -X POST https://api.eu.sparkpost.com/api/v1/transmissions -H 'Authorization: <APIKEY>' -H 'Content-Type: application/json' -d '{
   "options":{
      "open_tracking":false,
      "click_tracking":false,
      "inline_css":false
   },
   "recipients":[
      {
         "address":{
            "email":"user@domain.tld",
            "name":"user"
         }
      }
   ],
   "content":{
      "from":{
         "name":"sender",
         "email":"sender@domain.tld"
      },
      "reply_to":"replyto@domain.tld",
      "subject":"subject",
      "text":"textbody",
      "attachments":[
         {
            "name":"attachmentname.pdf",
            "type":"application/pdf",
            "data":"'$(cat test.pdf | base64 --wrap=0)'"
         }
      ]
   }
}'

会话只是一个映射,我们在其中添加了字符串常量的键和异常的值。 对于所有测试,除最后一个测试外,我们都进入最后一个else块,在最终测试中,我们为“ isAjax”返回true。

答案 1 :(得分:0)

虽然这不是Grails,但它是SpringBoot 2.0。

如果将failureHandler暴露为bean,则可以对其进行监视。

@SpyBean
AuthenticationFailureHandler failureHandler;

,只需验证是否已引发异常

Mockito.verify(failureHandler).onAuthenticationFailure(
    any(),
    any(),
    any(AccountExpiredException.class)
);

一个简单的test如下所示:

@Test
public void accountExpired() throws Exception {
    doReturn(user
        .username("expired")
        .accountExpired(true)
        .build()
    ).when(userDetailsService).loadUserByUsername(any(String.class));
    mvc.perform(
        MockMvcRequestBuilders.post("/login")
            .param("username", "expired")
            .param("password", "password")
    )
        .andExpect(status().is4xxClientError())
        .andExpect(unauthenticated())
    ;
    Mockito.verify(failureHandler).onAuthenticationFailure(
        any(),
        any(),
        any(AccountExpiredException.class)
    );
}

https://github.com/fhanik/spring-security-community/处的所有样本