java反射調用dubbo接口


需求:項目增加冪等

場景:
1.三個項目:a 、b、c
2.a項目加冪等
3.b項目dubbo調用項目a的時候超時沒有獲取返回結果,增加重試機制(非立即重試,3min or 5min 后重試)
4.c項目是一個異步的job項目,用來接收mq,異步處理,管理task等。

方案:
1.a項目設置請求流水id,將請求先存入redis緩存,處理完成之后更新redis中的狀態,同一個流水id認為是重復提交,不進行業務處理,直接返回redis中的狀態
2.b項目捕獲調用a項目的超時異常,存入redis隊列
3.c項目啟動兩個task,task1用來獲取redis隊列里面的信息,落庫。task2用來掃庫,及重試。

重點:
1.c項目只是異步接口消息沒有業務處理邏輯
2.task2重試的時候需要通過dubbo接口調用b來進行重新發起請求,及后續處理。

這里重點分享一下通過反射機制調用dubbo接口(map為請求參數)

String inter = "com.xxx.xxx.xxx.xxx.xxx.xxx";
Class<?> mClass = Class.forName(inter);
Method method = mClass.getMethod("methodNamexxx",new Class[]{String.class});
Object object = method.invoke(mClass.newInstance(),JSON.toJSONString(map));   

圈重點:

1.inter需要是serviceImpl實現類,如果是interface的話,會報

Caused by: java.lang.NoSuchMethodException: com.xxx.xxx.xxx.xxx.xxx.<init>()

2.invoke(Object obj,Object... args) 這里的obj需要newInstance()一下,否則會報

java.lang.IllegalArgumentException: object is not an instance of declaring class

 

調用dubbo接口的寫法:(map為請求參數)

String inter = "com.xxx.xxx.xxx.IxxxService";
String methodName = "xxxxx";
Class<?> mClass = Class.forName(inter); Map<String,Object> map = new HashMap<>(); AbstractApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml"); Object obj = context.getBean(this.getBeanName(inter)); Method method = mClass.getMethod(methodName,new Class[]{Object.class}); Object object = method.invoke(obj,JSON.toJSON(map));
public String getBeanName(String str){
        String name = str.substring(str.lastIndexOf(".")+2,str.length());
        name = name.substring(0,1).toLowerCase() + name.substring(1,name.length());
        return name;
    }

通過解析inter獲取beanName,通過spring獲取bean的方式獲取對象進行反射調用。

將interface及method配置到數據庫中,就能實現不用改動代碼進行調用的操作了。  

  

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM