内容简介:RPC框架中一般都有3个角色:服务提供者、服务消费者和注册中心。服务提供者将服务注册到注册中心,服务消费者从注册中心拉取服务的地址,并根据服务地址向服务提供者发起RPC调用。动态代理在这个RPC调用的过程中有什么作用?对于服务消费者,一般只会依赖服务接口,而服务的具体实现是在服务提供者这一端的,服务消费者和服务提供者分别部署在不同的机器上,服务消费者调用接口中的方法时怎么能够得到结果呢?JDK的动态代理就派上用场了。服务消费者使用JDK的动态代理技术,可以创建接口的代理对象,并在回调函数中将自己要调用的接口
RPC框架中一般都有3个角色:服务提供者、服务消费者和注册中心。服务提供者将服务注册到注册中心,服务消费者从注册中心拉取服务的地址,并根据服务地址向服务提供者发起RPC调用。动态代理在这个RPC调用的过程中有什么作用?对于服务消费者,一般只会依赖服务接口,而服务的具体实现是在服务提供者这一端的,服务消费者和服务提供者分别部署在不同的机器上,服务消费者调用接口中的方法时怎么能够得到结果呢?JDK的动态代理就派上用场了。服务消费者使用JDK的动态代理技术,可以创建接口的代理对象,并在回调函数中将自己要调用的接口名称、方法签名信息通过http或者tcp的方式发送给服务提供者,服务提供者再通过反射的方式调用本地的服务,最后将结果通过http或tcp的方式返回给消费者。
下面是一个简单的演示程序:
import Java.lang.reflect.InvocationHandler; import java.lang.reflect.Method; import java.lang.reflect.Proxy; import java.util.HashMap; import java.util.Map; /** * 动态代理在RPC中的使用 * * @author syj */ public class JDKProxyTest { // --------------------------- 模拟RPC客户端 --------------------------- // 客户端依赖服务端的接口(实现类在服务端) private static IUserService userService; public static void main(String[] args) { // 根据接口创建代理对象 userService = (IUserService) Proxy.newProxyInstance( JDKProxyTest.class.getClassLoader(), new Class[]{IUserService.class}, new InvocationHandler() { // 在回调方法模拟进行RPC调用(通过http或者tcp与服务端通信) @Override public Object invoke(Object proxy, Method method, Object[] params) throws Throwable { return rpcInvoke(IUserService.class.getSimpleName(), method.getName(), method.getParameterTypes(), params); } } ); // 本地调用 String result = userService.sayHello("hello"); System.out.println(">>>> result =" + result); } // --------------------------- 模拟RPC服务端 --------------------------- /** * 反射调用 * * @param methodName 方法名称 * @param parameterTypes 方法参数类型 * @param parameters 方法参数 * @return */ private static Object rpcInvoke(String interfaceName, String methodName, Class<?>[] parameterTypes, Object[] parameters) { Object result = null; try { // 根据接口名称从Bean容器中获取Bean实例 Object serviceBean = beanMap.get(interfaceName); // 反射调用 Class<?> serviceClass = serviceBean.getClass(); Method method = serviceClass.getMethod(methodName, parameterTypes); method.setAccessible(true); // 得到调用结果 result = method.invoke(serviceBean, parameters); } catch (Exception e) { e.printStackTrace(); } return result; } // 模拟Bean容器, key为接口名称, value为bean实例 private static Map<String, Object> beanMap = new HashMap<String, Object>() {{ put("IUserService", new UserServiceImpl()); }}; }
接口(服务提供者和服务的消费者都会依赖该接口):
public interface IUserService { String sayHello(String content); }
服务提供者实现类:
public class UserServiceImpl implements IUserService { @Override public String sayHello(String content) { return content + "::" + System.currentTimeMillis(); } }
Linux公社的RSS地址 : https://www.linuxidc.com/rssFeed.aspx
本文永久更新链接地址: https://www.linuxidc.com/Linux/2019-06/158897.htm
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持 码农网
猜你喜欢:本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
Web之困:现代Web应用安全指南
(美)Michal Zalewski / 朱筱丹 / 机械工业出版社 / 2013-10 / 69
《web之困:现代web应用安全指南》在web安全领域有“圣经”的美誉,在世界范围内被安全工作者和web从业人员广为称道,由来自google chrome浏览器团队的世界顶级黑客、国际一流安全专家撰写,是目前唯一深度探索现代web浏览器安全技术的专著。本书从浏览器设计的角度切入,以探讨浏览器的各主要特性和由此衍生出来的各种安全相关问题为主线,深入剖析了现代web浏览器的技术原理、安全机制和设计上的......一起来看看 《Web之困:现代Web应用安全指南》 这本书的介绍吧!