首页 > 作文

Feign远程调用传递对象参数并返回自定义分页数据的过程解析

更新时间:2023-04-06 04:31:35 阅读: 评论:0

feign介绍

feign是netflix公司开源的轻量级rest客户端,使用feign可以非常方便的实现http 客户端。spring cloud引入feign并且集成了ribbon实现客户端负载均衡调用。

feign测试

1.在yml文件里面增加了配置信息

feign: httpclient:  enabled: true

2.在客户端pom.xml文件中引入的依赖(消费者端)

<!-- 配置feign 发送请求使用 httpclient,而不是java原生 -->    <dependency>      <groupid>org.apache.httpcomponents</groupid>     2049年的世界 <artifactid>httpclient</artifactid>    </dependency>   <!-- 此处不使用apache httpclient 的httpclient依赖,一定要使用下面这个依赖,因为我们要返回的是pojo类-->    <dependency>      <groupid>io.github.openfeign</groupid>      <artifactid>feign-httpclient</artifactid>      <version>10.1.0</version>    </dependency>

此处注意

此处依赖为什么使用io.github.openfeign的httpclient,而不使用apache 的httpclient替换feign原生httpclient。

看了很多文章,都是说引用这个依赖:

<!-- 使用apache httpclient替换feign原生httpclient--><!--    <dependency>--><!--      <groupid>com.netflix.feign</groupid>--><!--      <artifactid>feign-httpclient</artifactid>--><!--      <version>8.16.1</version>--><!--    </dependency>-->

但是不知道哪里的问题,在获取返回结果时一直报错:

caud by: java.lang.nosuchmethoderror: feign.respon.create(iljava/lang/string;ljava/util/map;lfeign/respon$body;)lfeign/respon;

查看源码得知,openfeign在接受返回值时调用的不是httpclient的feign-core包的代码而是调用的本身的feign-core的代码,而本身的feign-core包中的respon类没有create方法。两个feign-core包中的retryer接口不一致导致的,openfeign的feign-core版本为10.1.0 httpclient的版本为8.16.1。

找了半天问题,最后就把httpclient的依赖换成代码块中的依赖就ok了。

3.服务调用端接口为

此处使用post请求,第6步有解释。

@slf4j@requestmapping("/list")@restcontrollerpublic class webquerylistcontroller {    @autowired  private tourismlistrvice listrvice;   @postmapping("/ad/allbyquery")  public apiresult<page<tourismad>> allbyquery(@requestbody tourismadquery adquery){    apiresult<page<tourismad>> pageapiresult = listrvice.lectalladbyquery(adquery);    return pageapiresult;  }

我的tourismadquery类继承了page类(似乎没有影响)

@datapublic class tourism杜甫的诗被称为adquery extends page<tourismad> {  /**  * 标题  */  private string title;  。。。。。。。}

4.服务调用端rvice代码

此处@postmapping地址为服务端提供的api接口地址

@feignclient(name = "fisher-back-rvice", fallback = tourismlistfallback.class, configuration = feignconfig.class)public interface tourismlistrvice {  /**  * 分页查询广告根据查询条件  * @param adquery  * @return  */ @postmapping(value = "/ad/get/allbyquery")  apiresult<page<tourismad>> lectalladbyquery(tourismadquery adquery);

5.服务调用端fallback为

@slf4j@rvicepublic class tourismlistfallback implements tourismlistrvice {  /**  * 分页查询广告根据查询条件  *  * @param adquery  * @return  */  @override  public apiresult<page<tourismad>> lectalladbyquery(tourismadquery adquery) {    log.error("调用 lectalladbyqudont say goodbyeery 方法异常,参数:{}", adquery);    return null;  }

6.服务提供端代码为

此处传进来的参数是一个pojo类,如果不使用@requestbody注解 的话,feign远程调用时参数是无法被接收到的。

虽然获取数据时,大多数使用 get请求方法,但是get方法无法接收@requestbody参数体。

所以只好改get请求为post请求。

@restcontroller@requestmapping("/ad")public class tourismadcontroller extends bacontroller<tourismadrvice, tourismad, integer> {  @autowired  private tourismadrvice adrvice; @apioperation(value = "分页查询广告根据查询条件", notes = "分页查询广告根据查询条件", httpmethod = "post")  @postmapping("/get/allbyquery")  public apiresult<page<tourismad>> allbyquery(@requestbody tourismadquery adquery){    return adrvice.lectallbyquery(adquery);  }

7.测试

调用接口http://localhost:9009/list/ad/allbyquery 传递json格式参数即可:

{ "address": "", "title": "广告位1", "size": 6}

成功分页获取数据 自定义的返回类型数据:

{ 一级学科和二级学科是什么意思"data": {  "records": [   {    "id": 1,    "title": "广告位1",    "description": "招商",    "sort": 0,    "datetime": "2019-09-26 17:46:50",    "updatetime": "2019-09-26 17:46:50",    "peopleid": 0,    "display": 0,    "content": "04004",    "file": "444//44.jpg",    "leaperson": "找找",    "address": "杭州市",    "idcard": "1154465656656",    "phone": "131654799"   }  ],  "total": 1,  "size": 6,  "current": 1,  "archcount": true,  "pages": 1 }, "code": 200, "message": "分页获取成功"}

feign调用分页接口报错:method has too many body parameters

接口定义:

@apioperation(value = "分页查询会话")@postmapping(routes.ssions_query)jsonresult<pagination<ssioninfo>> queryssions(@requestbody @valid ssionsqo qo,@pageabledefault(size = 20, sort = "id", direction = sort.direction.desc) pageable pageable);

服务消费方调用报错:

method has too many body parameters: public abstract com.xingren.common.data.jsonresult com.xingren.xxx.yyy.contract.api.controller.issioncontroller.queryssions(com.xingren.xxx.yyy.contract.qo.ssionsqo,org.springframework.data.domain.pageable)

解决方法

通过搜索、调研,目前有三种解决方法:

1、将分页属性直接通过入参传递,接口定义如下:

@apioperation(value = "分页查询会话")@postmapping(routes.ssions_query)jsonresult<pagination<ssioninfo>> queryssions(@requestbody @valid ssionsqo qo,@requestparam("page") integer page, @requestparam("size") integer size, @requestparam("sort") sort sort);

2、将分页对象冗余在qo中(通过继承实现):

@data@noargsconstructor@apimodel(value = "查询会话")public class ssionsqo extends pageableparam {@apiparam(value = "会话id列表")private list<long> ssionidin = lists.newarraylist();...}

3、通过注解传递(参考:issue):

服务提供方定义注解:

@target(elementtype.parameter)@retention(retentionpolicy.runtime)public @interface pageableparam {}

服务提供方定义接口:

@apioperation(value = "分页查询会话")@postmapping(routes.ssions_query)jsonresult<pagination<ssioninfo>> queryssions(@requestbody @valid ssionsqo qo,@pageableparam @springquerymap pageable pageable);

服务消费方定义processor:

@beanpublic pageableparamprocessor pageableparamprocessor() {    return new pageableparamprocessor();} public static class pageableparamprocessor implements annotatedparameterprocessor {     private static final class<pageableparam> annotation = pageableparam.class;     @override    public class<? extends annotation> getannotationtype() {        return annotation;    }     @override    public boolean processargument(annotatedparametercontext context, annotation annotation, method method) {        int parameterindex = context.getparameterindex();        methodmetadata data = context.getmethodmetadata();        data.querymapindex(parameterindex);        return true;    } }

服务消费方自定义pageableutil:

public class pageableutil extends pagerequest implements map<string, object> {  public static final string page = "page";  public static final string size = "size";  public static final string sort = "sort";  @delegate  protected map<string, object> delegate = maps.newhashmap();  public pageableutil(int page, int size, sort sort) {    super(page, size, sort);    delegate.put(page, page);    delegate.put(size, size);    if (objects.nonnull(sort)) {      delegate.put(sort, sort.tostring().replace(": ", ","));    }  }  public pageableutil(int page, int size) {    super(page, size);    delegate.put(page, page);    delegate.put(size, size);  }}

定义pageableutil原因:主要是因为feign对queryma小学教育教学工作总结p类型参数的序列化和反序列化的言七墨方式与sort.order的不兼容,导致排序失效。

服务消费方调用方式:

ssionsqo qo = ssionsqo.builder().ssionidin(collections.singletonlist(20l)).build();jsonresult<pagination<ssioninfo>> pageinfo = ssioncontract.queryssions(qo, new pageableutil(0, 5, new sort(sort.direction.desc,

以上为个人经验,希望能给大家一个参考,也希望大家多多支持www.887551.com。

本文发布于:2023-04-06 04:31:29,感谢您对本站的认可!

本文链接:https://www.wtabcd.cn/fanwen/zuowen/12b92d6ef76f7da580cc335d5c01d509.html

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。

本文word下载地址:Feign远程调用传递对象参数并返回自定义分页数据的过程解析.doc

本文 PDF 下载地址:Feign远程调用传递对象参数并返回自定义分页数据的过程解析.pdf

下一篇:返回列表
标签:分页   接口   参数   代码
相关文章
留言与评论(共有 0 条评论)
   
验证码:
Copyright ©2019-2022 Comsenz Inc.Powered by © 专利检索| 网站地图