Feignインターフェース方法戻り値設定方式


紹介します
マイクロサービスの広範な応用に伴い、マイクロサービスを利用してプロジェクト開発を行う企業が増えており、各サービス間ではフィーリングを通じて通信を行う必要があるため、フィーリングコールインターフェースでは他のサービスインターフェースの異なるタイプのリターン値を受け入れる方法がある。
二、戻り値設定
1、コールされたサービスインターフェースに従って同じ返却タイプを設定する
紹介:マイクロサービスAインターフェースgetUserはList<User>タイプに戻り、マイクロサービスBはfeign呼び出し方法によっても同じ結果タイプに戻る。
特徴:戻るタイプは一つ一つ対応していますが、呼び出し時に転化する必要がなく、そのまま持ってきてもいいです。
短所:拡張性が良くなく、メンテナンス性がプラスされていません。
現在のspringbootの開発では、インターフェースは一般的にjsonタイプのデータに戻ります(つまり@restControllerを使ったり@ResonseBodyを使って注解したりします)。対象または対象のセットでも同じです。または他の自分でパッケージした返却対象です。もし多くの異なるリターンオブジェクトがある場合、これらのリターンオブジェクトがAサービスで修正された場合、対応するBサービスのfeignインターフェースでも修正されます。かなり面倒で、javaインターフェース向けプログラミング思想に合わないです。
2、全部Stringに設定されています。
紹介:マイクロサービスAインターフェースは@restControllerまたは@ResonseBodyによって修正されます。私はすべてマイクロサービスBfeignインターフェースでSteringを使って受け入れます。
特徴:Steringによるリターンパラメータを受け付け、フォーマットが一致しています。
短所:後の呼び出しは変換が必要です。
コード紹介:

//    A controller     @restController  
@PostMapping(value="/getAllQuestionBank",produces = MediaType.APPLICATION_JSON_UTF8_VALUE)
	public List<QuestionBankDto> getAllQuestionBank(){
		return baseinfoQuestionMange.getAllQuestionBank();
}
 
//    B feign     String    
@PostMapping(value="/baseinfo/getAllQuestionBank")
String getAllQuestionBank();
 
//    B      feign        List<QuestionBankDto>   
 
//              ,      try catch    
String questionBankInfo = baseInfoApi.getAllQuestionBank();
List<QuestionBankDto> mysqlQuestionBank = objectMapper.readValue(questionBankInfo,new TypeReference<ArrayList<QuestionBankDto>>(){});

あなたがspringbootを導入して依存する限り、それはデフォルトでJackson jarカバンを導入しました。

注意事項:この方式を使う時、Object Mapperをbean容器に配置する必要があります。

3、まとめ
プロジェクトは違っています。需要は違っています。二つの方法は誰が間違っていますか?
Feignはこの数日間の問題を使っています。
事の発端は、私がパAモジュールサービスを呼び出そうとしたことから始まります。
Feignは今教程が多くて、pomを紹介します。

 <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-openfeign</artifactId>
        </dependency>
インターフェースを自分で定義します。

@FeignClient(name = "weixinTokenClient", url = "https://qyapi.weixin.qq.com/cgi-bin")
public interface IWeiXinTokenClient {
   /**
    *      token
    * @param corpid
    * @param corpsecret
    * @return
    */
   @RequestMapping(value = "/gettoken", method = RequestMethod.GET)
   WeiXinTokenResultModel getToken(@RequestParam String corpid, @RequestParam String corpsecret);
}
testクラスのテストを書いて、完璧に戻ってきます。自分で似たような項目を書いたので、lemur-httpを見てもいいです。原理は大体同じです。考えたら簡単です。でも、後の問題は出てきます。
1.nacosの設定はサービスをもらえません。
理由は:nacos登録サービスはlemur-adminとlemur-paasというサービスレベルのサービスのみ登録されています。サービスアドレスを取得するにはlemur-adminサービスが必要ですが、adminでpaasインターフェースを呼び出す時には

@FeignClient(value = "paasUserFacade", contextId = "lemur-paas", path = "/im/user")
public interface IPaasUserFacade extends IBaseController<PaasUserRequestModel> {
}
@Feign Client注释value、name、contextId、serviceIdは全部nameとしていますので、nacosの住所を取得するところはpaasUser Facadeでマッチングしています。ぜんぜん取れません。最後にNパスと一緒に来ました。解決方法を探していません。自分はまだソースFeignClintFactornを変更しました。また、contextIdに別名を登録しなくても、意味が大きくなく、また名前を重ねて、contextIdをサービスIdとして、feignはtargetを通じてアドレス解析をするので、targtのurlアドレスをlemur-paas/im/userに変更すればいいです。

<T> T getTarget() {
  FeignContext context = this.applicationContext.getBean(FeignContext.class);
  Feign.Builder builder = feign(context);
  if (!StringUtils.hasText(this.url)) {
   if (StringUtils.hasText(this.contextId) && !this.name.startsWith("http")){
    this.url =  "http://" + this.contextId;
   }else if (StringUtils.hasText(this.contextId)){
    this.url =  this.contextId;
   } else if (!this.name.startsWith("http")) {
    this.url = "http://" + this.name;
   }
   else {
    this.url = this.name;
   }
   this.url += cleanPath();
   return (T) loadBalance(builder, context,
     new HardCodedTarget<>(this.type, this.name, this.url));
  }
  if (StringUtils.hasText(this.url) && !this.url.startsWith("http")) {
   this.url = "http://" + this.url;
  }
  String url = this.url + cleanPath();
  Client client = getOptional(context, Client.class);
  if (client != null) {
   if (client instanceof LoadBalancerFeignClient) {
    // not load balancing because we have a url,
    // but ribbon is on the classpath, so unwrap
    client = ((LoadBalancerFeignClient) client).getDelegate();
   }
   builder.client(client);
  }
  Targeter targeter = get(context, Targeter.class);
  return (T) targeter.target(this, builder, context,
    new HardCodedTarget<>(this.type, this.name, url));
 }
ソースを変更したら、お互いに呼び出すことができます。
2.fastjsonはabstract classをサポートしていません。間違ったことを報告しないで、直接nullに戻ります。
風鈴が統一して戻ってくるのは全部Resonseの対象ですので、汎型を加えて、結局どうやって呼び出して戻ってきたのは全部nullです。呼び出しられたサービスが要求を受けて戻ってきたのかを見てみます。これはクライアントの問題です。最初は汎型解析の問題だと思って、全体の呼び出し解析チェーンを追跡しました。

ReflectiveFeign.invoke->
SynchronousMethodHandler.invoke->
executeAndDecode->decode(    )->
ResponseEntityDecoder.decode->
SpringDecoder.decode->
HttpMessageConverterExtractor.extractData(    )->
FastJsonHttpMessageConverter(      ).read(type,clazz,inputMessage)->
parseObject(is)
そして何を発見しましたか?fastjsonは対象を具体化できません。あなたにも間違いを報告します。abstractを除いて正常に戻ります。
3.スプリングgatewayはwebをサポートしていません。
spring gatewayはwebfluxを使って書いていますので、web容器ではないのでwebを導入することができません。feignを導入する時はwebを削除します。でないと起きられません。

 <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-openfeign</artifactId>
            <exclusions>
                <exclusion>
                    <artifactId>spring-boot-starter-web</artifactId>
                    <groupId>org.springframework.boot</groupId>
                </exclusion>
            </exclusions>
        </dependency>
また、spring gatewayもプロファイルの読み込みをサポートしていません。同じ理由で、J 2 cacheのようなファイル配置は読み込めません。
以上は個人の経験ですので、参考にしていただければと思います。