Mockito:如何使服务调用抛出异常

时间:2018-01-23 16:15:51

标签: java mocking mockito hystrix

我班上有Hystrix命令,我需要测试。我可以模拟除了后备之外的所有代码。要执行回退,我需要使用我的hystrix包装方法来抛出超时异常。我不明白该怎么做。有人可以帮我吗?我尝试在测试类上使用@Enablecircuitbreaker打开电路,但是没有调用任何Hystrix异常:(

     @Mock
     private MDMConnectorService service;
     @InjectMocks
     private AIAUtilities aiaUtilities;

     @Test
  public void testFetchCustomerAccountDetailsHystrixTimeoutException() throws Exception {
    try {
      ConfigurationManager.getConfigInstance()
          .setProperty("hystrix.command.AIAClientCommand.circuitBreaker.forceOpen", "true");
      Mockito.when(service.fetchCustomerAccount(any(GetCustomerAccountType.class))).thenReturn(getTestAIARecord());
      GetCustomerAccountResponseType responseType = aiaUtilities
          .fetchCustomerAccountDetails(accountNumber);
      Assert.assertFalse(true);// if the flow came here, the test case has failed
    } catch (Exception ex) {
      if (ex instanceof DataAccessException) {
        assertEquals(Constants.ERRCODE_AIA_QUERY_TIMED_OUT,
            ((DataAccessException) ex).getErrorCode());
      } else {
        throw ex;
      }
    }
    finally {
      ConfigurationManager.getConfigInstance()
          .setProperty("hystrix.command.AIAClientCommand.circuitBreaker.forceOpen", "false");
    }
  }

在此测试中,由hystrix包装的命令在

处被调用
    GetCustomerAccountResponseType responseType = aiaUtilities
      .fetchCustomerAccountDetails(accountNumber);

具有hystrix命令和相应回退的AIAUtilities的代码是

    @HystrixCommand(commandKey = "AIAClientCommand", fallbackMethod = "aiaClientCommandFallback")
    public GetCustomerAccountResponseType fetchCustomerAccountDetails(String accountNumber)
        throws DataAccessException {
      GetCustomerAccountResponseType response;

      try {

        if (generalUtil.isObjectEmpty(authHeader)) {
        authHeader = iamUtilities.createAuthHeaderAndRenewOfflineTicket();
      }
      factory = getFactory();
      request = getRequest();
      accountNumberType = getAccountNumberType();
      accountNumberType.setValue(accountNumber);
      request.setCustomerAccountNumber(accountNumberType);
      request.setSourceId(Constants.VAL_QUICKBASE_SOURCE_AIA);
      serviceClass = getServiceClass();
      service = getService();
      provider = getProvider();;
      provider.getRequestContext().put("Authorization", authHeader);
      provider.getRequestContext().replace("SOAPAction", "fetchCustomerAccount");
      provider.getRequestContext().put("Content-Type", "text/xml");

      response = service.fetchCustomerAccount(request);
      } catch (DataAccessException e) {
        throw e;
      }
      catch (Exception e) {
        if(e instanceof HystrixRuntimeException && e.getCause() instanceof TimeoutException) {
          DataAccessException dataAccessException = (DataAccessException) ((HystrixRuntimeException) e)
              .getFallbackException().getCause();
          throw new DataAccessException(dataAccessException.getErrorCode(),
              "Exception in validateLicense.fetchCustomerAccountDetails::" + e.getMessage(),e);
        }
        else
        throw new DataAccessException(Constants.ERRCODE_AIA_EXCEPTION,
            "Exception in validateLicense.fetchCustomerAccountDetails:::" + e.toString(), e);
      }
      return response;
    }

    private GetCustomerAccountResponseType aiaClientCommandFallback(String accountNumber, Throwable e)
        throws DataAccessException {
      logger.error("Inside AIAClientCommandFallback : Error is ::" + e.toString());
      if(e instanceof HystrixTimeoutException)
        throw new DataAccessException(Constants.ERRCODE_AIA_QUERY_TIMED_OUT,
            "Exception in AIAClientCommandFallback::" + e.toString(),e);
      else if(e instanceof DataAccessException)
        throw (DataAccessException)e;
      else
        throw new DataAccessException(Constants.ERRCODE_AIA_EXCEPTION,
          "Inside AIAClientCommandFallback : Error is ::" + e.toString(), e);
    }

1 个答案:

答案 0 :(得分:4)

不是在你的模拟fetchCustomerAccount中返回一些内容,而只是通过thenThrow在那里抛出异常:

Mockito.when(service.fetchCustomerAccount(any(GetCustomerAccountType.class))).thenThrow(new RuntimeException("Timeout"));