3

私はDropwizardアプリケーションを作成しておりFeign、外部サービスへのクライアント呼び出しを構築するために使用しています。私は次のfeign.Builderように登録しているカスタムエンコーダーとデコーダーを持っています:

    this.feignBuilder = Feign.builder()
            .contract(new JAXRSContract()) // we want JAX-RS annotations
            .encoder(new JacksonEncoder()) // same as what dropwizard is using
            .decoder(new CustomDecoder())
            .errorDecoder(new CustomErrorDecoder())
            .requestInterceptor(new AuthKeyInterceptor(config.getInterceptor()));

クライアント呼び出しの単体テストを書いてfeignいるので、偽の機械がエンコーダー/デコーダーのオーバーライドと例外のバブルをどのように処理するかを見ることができます。私は現在、偽のサーバーとの統合テストを書くことに興味がありません (これは、この状況のた​​めに書いている最も一般的なタイプのテストです)。

これは簡単です。feignリクエストを行うポイントをモックし、偽のレスポンスを返してもらいたいです。つまり、呼び出しをモックする必要があるため、リクエストがthis call sitefeign.Client.Default.executeになったときに偽の応答が返されます。そのモックがどのように見えるかの例:

String responseMessage = "{\"error\":\"bad\",\"desc\":\"blah\"}";
feign.Response feignResponse = FeignFakeResponseHelper.createFakeResponse(404,"Bad Request",responseMessage);
Client.Default mockFeignClient = mock(Client.Default.class);
try {
     when(mockFeignClient.execute(any(feign.Request.class),any(Request.Options.class))).thenReturn(feignResponse);
} catch (IOException e) {
     assertThat(true).isFalse(); // fail nicely
}

運がない。コード内のリクエストの呼び出しサイトに到達しても、Cleint.Defaultクラスはモックされません。私は何を間違っていますか?

4

2 に答える 2

3

前述のように、Mockito は十分に強力ではありません。手動モックでこれを解決しました。

思ったより簡単です:

MyService.Java

public class MyService{
    //My service stuff      

    private MyFeignClient myFeignClient;

    @Inject //this will work only with constructor injection
    public MyService(MyFeignClient myFeignClient){
        this.MyFeignClient = myFeignClient
    }


    public void myMethod(){
        myFeignClient.remoteMethod(); // We want to mock this method
    }
}

MyFeignClient.Java

@FeignClient("target-service")
public interface MyFeignClient{

    @RequestMapping(value = "/test" method = RequestMethod.GET)
    public void remotemethod();
}

feignclient をモックしながら上記のコードをテストする場合は、次のようにします。

MyFeignClientMock.java

@Component
public class MyFeignClientMock implements MyFeignClient {

    public void remoteMethod(){
         System.out.println("Mocked remoteMethod() succesfuly");
    }
}

MyServiceTest.java

@RunWith(SpringJUnit4ClassRunner.class)
public class MyServiceTest {

    private MyService myService;

    @Inject
    private MyFeignClientMock myFeignClientMock;

    @Before
    public void setUp(){
       this.myService = new MyService(myFeignClientMock); //inject the mock
    }

    //Do tests normally here...
}
于 2016-03-27T06:54:27.353 に答える