RPC过程简单实现

非原创,转自 https://blog.csdn.net/Evankaka/article/details/71196212


1、主要代码


    
    
  1. package com.github.distribute.rpc;
  2. import java.io.ObjectInputStream;
  3. import java.io.ObjectOutputStream;
  4. import java.lang.reflect.InvocationHandler;
  5. import java.lang.reflect.Method;
  6. import java.lang.reflect.Proxy;
  7. import java.net.ServerSocket;
  8. import java.net.Socket;
  9. public class RpcFramework {
  10. public static void export(final Object service, final Class interfaceClazz, int port) throws Exception {
  11. if (service == null) {
  12. throw new IllegalAccessException( "service instance == null");
  13. }
  14. if (port < 0 || port > 65535) {
  15. throw new IllegalAccessException( "Invalid port " + port);
  16. }
  17. System.out.println( "Export service " + service.getClass().getName() + " on port " + port);
  18. ServerSocket server = new ServerSocket(port);
  19. //循环等待,每来一个请求开启一条线程进行处理
  20. for (;;) {
  21. final Socket socket = server.accept(); //tcp阻塞等待
  22. try {
  23. new Thread( new Runnable() {
  24. @Override
  25. public void run() {
  26. try {
  27. try {
  28. ObjectInputStream input = new ObjectInputStream(socket.getInputStream());
  29. try {
  30. String interfaceName = input.readUTF();
  31. String methodName = input.readUTF();
  32. Class<?>[] parameterTypes = (Class<?>[]) input.readObject();
  33. Object[] arguments = (Object[]) input.readObject();
  34. ObjectOutputStream output = new ObjectOutputStream(socket.getOutputStream());
  35. try {
  36. if (!interfaceName.equals(interfaceClazz.getName())) {
  37. throw new IllegalAccessException( "Interface wrong, export:" + interfaceClazz
  38. + " refer:" + interfaceName);
  39. }
  40. Method method = service.getClass().getMethod(methodName, parameterTypes);
  41. Object result = method.invoke(service, arguments);
  42. output.writeObject(result);
  43. } catch (Throwable t) {
  44. output.writeObject(t);
  45. } finally {
  46. output.close();
  47. }
  48. } catch (Throwable t) {
  49. t.printStackTrace();
  50. } finally {
  51. input.close();
  52. }
  53. }
  54. finally {
  55. socket.close();
  56. }
  57. } catch (Exception e) {
  58. e.printStackTrace();
  59. }
  60. }
  61. }).start();
  62. } catch (Exception e) {
  63. e.printStackTrace();
  64. }
  65. }
  66. }
  67. @SuppressWarnings( "unchecked")
  68. public static <T> T refer(final Class<T> interfaceClass, final String host, final int port) throws Exception {
  69. if (interfaceClass == null) {
  70. throw new IllegalAccessException( "Interface class == null");
  71. }
  72. if (!interfaceClass.isInterface()) {
  73. throw new IllegalAccessException(interfaceClass.getName() + " must be interface");
  74. }
  75. if (host == null || host.length() == 0) {
  76. throw new IllegalAccessException( "host == null");
  77. }
  78. if (port <= 0 || port > 65535) {
  79. throw new IllegalAccessException( "Invalid port " + port);
  80. }
  81. System.out.println( "Get remote service " + interfaceClass.getName() + " from server " + host + ":" + port);
  82. return (T) Proxy.newProxyInstance(interfaceClass.getClassLoader(), new Class<?>[] { interfaceClass },
  83. new InvocationHandler() {
  84. @Override
  85. public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
  86. // TODO Auto-generated method stub
  87. Socket socket = new Socket(host, port);
  88. try {
  89. ObjectOutputStream output = new ObjectOutputStream(socket.getOutputStream());
  90. try {
  91. output.writeUTF(interfaceClass.getName());
  92. output.writeUTF(method.getName());
  93. output.writeObject(method.getParameterTypes());
  94. output.writeObject(args);
  95. ObjectInputStream input = new ObjectInputStream(socket.getInputStream());
  96. try {
  97. Object result = input.readObject();
  98. if (result instanceof Throwable) {
  99. throw (Throwable) result;
  100. }
  101. return result;
  102. } finally {
  103. input.close();
  104. }
  105. } finally {
  106. output.close();
  107. }
  108. } finally {
  109. socket.close();
  110. }
  111. }
  112. });
  113. }
  114. }

2、模拟接口

接口类


    
    
  1. package com.github.distribute.rpc;
  2. public interface HelloService {
  3. String hello();
  4. String hello(String name);
  5. }
实现类


    
    
  1. package com.github.distribute.rpc;
  2. public class HelloServiceImpl implements HelloService {
  3. @Override
  4. public String hello() {
  5. return "Hello";
  6. }
  7. @Override
  8. public String hello(String name) {
  9. return "Hello," + name;
  10. }
  11. }

3、接口提供者


    
    
  1. package com.github.distribute.rpc;
  2. public class RpcProvider {
  3. public static void main(String[] args) throws Exception {
  4. HelloService service = new HelloServiceImpl();
  5. RpcFramework.export(service, HelloService.class, 9000);
  6. }
  7. }
结果:


4、消费者


    
    
  1. package com.github.distribute.rpc;
  2. public class RpcConsumer {
  3. public static void main(String[] args) throws Exception {
  4. HelloService service = RpcFramework.refer(HelloService.class, "127.0.0.1", 9000);
  5. String result = service.hello( "rod");
  6. System.out.println(result);
  7. }
  8. }

结果:


非原创,转自 https://blog.csdn.net/Evankaka/article/details/71196212


1、主要代码


  
  
  1. package com.github.distribute.rpc;
  2. import java.io.ObjectInputStream;
  3. import java.io.ObjectOutputStream;
  4. import java.lang.reflect.InvocationHandler;
  5. import java.lang.reflect.Method;
  6. import java.lang.reflect.Proxy;
  7. import java.net.ServerSocket;
  8. import java.net.Socket;
  9. public class RpcFramework {
  10. public static void export(final Object service, final Class interfaceClazz, int port) throws Exception {
  11. if (service == null) {
  12. throw new IllegalAccessException( "service instance == null");
  13. }
  14. if (port < 0 || port > 65535) {
  15. throw new IllegalAccessException( "Invalid port " + port);
  16. }
  17. System.out.println( "Export service " + service.getClass().getName() + " on port " + port);
  18. ServerSocket server = new ServerSocket(port);
  19. //循环等待,每来一个请求开启一条线程进行处理
  20. for (;;) {
  21. final Socket socket = server.accept(); //tcp阻塞等待
  22. try {
  23. new Thread( new Runnable() {
  24. @Override
  25. public void run() {
  26. try {
  27. try {
  28. ObjectInputStream input = new ObjectInputStream(socket.getInputStream());
  29. try {
  30. String interfaceName = input.readUTF();
  31. String methodName = input.readUTF();
  32. Class<?>[] parameterTypes = (Class<?>[]) input.readObject();
  33. Object[] arguments = (Object[]) input.readObject();
  34. ObjectOutputStream output = new ObjectOutputStream(socket.getOutputStream());
  35. try {
  36. if (!interfaceName.equals(interfaceClazz.getName())) {
  37. throw new IllegalAccessException( "Interface wrong, export:" + interfaceClazz
  38. + " refer:" + interfaceName);
  39. }
  40. Method method = service.getClass().getMethod(methodName, parameterTypes);
  41. Object result = method.invoke(service, arguments);
  42. output.writeObject(result);
  43. } catch (Throwable t) {
  44. output.writeObject(t);
  45. } finally {
  46. output.close();
  47. }
  48. } catch (Throwable t) {
  49. t.printStackTrace();
  50. } finally {
  51. input.close();
  52. }
  53. }
  54. finally {
  55. socket.close();
  56. }
  57. } catch (Exception e) {
  58. e.printStackTrace();
  59. }
  60. }
  61. }).start();
  62. } catch (Exception e) {
  63. e.printStackTrace();
  64. }
  65. }
  66. }
  67. @SuppressWarnings( "unchecked")
  68. public static <T> T refer(final Class<T> interfaceClass, final String host, final int port) throws Exception {
  69. if (interfaceClass == null) {
  70. throw new IllegalAccessException( "Interface class == null");
  71. }
  72. if (!interfaceClass.isInterface()) {
  73. throw new IllegalAccessException(interfaceClass.getName() + " must be interface");
  74. }
  75. if (host == null || host.length() == 0) {
  76. throw new IllegalAccessException( "host == null");
  77. }
  78. if (port <= 0 || port > 65535) {
  79. throw new IllegalAccessException( "Invalid port " + port);
  80. }
  81. System.out.println( "Get remote service " + interfaceClass.getName() + " from server " + host + ":" + port);
  82. return (T) Proxy.newProxyInstance(interfaceClass.getClassLoader(), new Class<?>[] { interfaceClass },
  83. new InvocationHandler() {
  84. @Override
  85. public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
  86. // TODO Auto-generated method stub
  87. Socket socket = new Socket(host, port);
  88. try {
  89. ObjectOutputStream output = new ObjectOutputStream(socket.getOutputStream());
  90. try {
  91. output.writeUTF(interfaceClass.getName());
  92. output.writeUTF(method.getName());
  93. output.writeObject(method.getParameterTypes());
  94. output.writeObject(args);
  95. ObjectInputStream input = new ObjectInputStream(socket.getInputStream());
  96. try {
  97. Object result = input.readObject();
  98. if (result instanceof Throwable) {
  99. throw (Throwable) result;
  100. }
  101. return result;
  102. } finally {
  103. input.close();
  104. }
  105. } finally {
  106. output.close();
  107. }
  108. } finally {
  109. socket.close();
  110. }
  111. }
  112. });
  113. }
  114. }

2、模拟接口

接口类


  
  
  1. package com.github.distribute.rpc;
  2. public interface HelloService {
  3. String hello();
  4. String hello(String name);
  5. }
实现类


  
  
  1. package com.github.distribute.rpc;
  2. public class HelloServiceImpl implements HelloService {
  3. @Override
  4. public String hello() {
  5. return "Hello";
  6. }
  7. @Override
  8. public String hello(String name) {
  9. return "Hello," + name;
  10. }
  11. }

3、接口提供者


  
  
  1. package com.github.distribute.rpc;
  2. public class RpcProvider {
  3. public static void main(String[] args) throws Exception {
  4. HelloService service = new HelloServiceImpl();
  5. RpcFramework.export(service, HelloService.class, 9000);
  6. }
  7. }
结果:


4、消费者


  
  
  1. package com.github.distribute.rpc;
  2. public class RpcConsumer {
  3. public static void main(String[] args) throws Exception {
  4. HelloService service = RpcFramework.refer(HelloService.class, "127.0.0.1", 9000);
  5. String result = service.hello( "rod");
  6. System.out.println(result);
  7. }
  8. }

结果:


猜你喜欢

转载自blog.csdn.net/weixin_42581112/article/details/89074725