Vous ne pouvez pas sélectionner plus de 25 sujets Les noms de sujets doivent commencer par une lettre ou un nombre, peuvent contenir des tirets ('-') et peuvent comporter jusqu'à 35 caractères.

ServerRpcManager.java 6.0KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192
  1. /*
  2. * Copyright 2000-2018 Vaadin Ltd.
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the "License"); you may not
  5. * use this file except in compliance with the License. You may obtain a copy of
  6. * the License at
  7. *
  8. * http://www.apache.org/licenses/LICENSE-2.0
  9. *
  10. * Unless required by applicable law or agreed to in writing, software
  11. * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
  12. * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
  13. * License for the specific language governing permissions and limitations under
  14. * the License.
  15. */
  16. package com.vaadin.server;
  17. import java.io.Serializable;
  18. import java.lang.reflect.Field;
  19. import java.lang.reflect.Method;
  20. import java.util.HashMap;
  21. import java.util.Map;
  22. import java.util.logging.Level;
  23. import java.util.logging.Logger;
  24. import com.vaadin.shared.communication.ServerRpc;
  25. /**
  26. * Server side RPC manager that handles RPC calls coming from the client.
  27. *
  28. * Each {@link RpcTarget} (typically a {@link ClientConnector}) should have its
  29. * own instance of {@link ServerRpcManager} if it wants to receive RPC calls
  30. * from the client.
  31. *
  32. * @since 7.0
  33. */
  34. public class ServerRpcManager<T extends ServerRpc> implements Serializable {
  35. private final T implementation;
  36. private final Class<T> rpcInterface;
  37. /**
  38. * Wrapper exception for exceptions which occur during invocation of an RPC
  39. * call.
  40. *
  41. * @author Vaadin Ltd
  42. * @since 7.0
  43. *
  44. */
  45. public static class RpcInvocationException extends Exception {
  46. public RpcInvocationException() {
  47. super();
  48. }
  49. public RpcInvocationException(String message, Throwable cause) {
  50. super(message, cause);
  51. }
  52. public RpcInvocationException(String message) {
  53. super(message);
  54. }
  55. public RpcInvocationException(Throwable cause) {
  56. super(cause);
  57. }
  58. }
  59. private static final Map<Class<?>, Class<?>> BOXED_TYPES = new HashMap<>();
  60. static {
  61. try {
  62. Class<?>[] boxClasses = new Class<?>[] { Boolean.class, Byte.class,
  63. Short.class, Character.class, Integer.class, Long.class,
  64. Float.class, Double.class };
  65. for (Class<?> boxClass : boxClasses) {
  66. Field typeField = boxClass.getField("TYPE");
  67. Class<?> primitiveType = (Class<?>) typeField.get(boxClass);
  68. BOXED_TYPES.put(primitiveType, boxClass);
  69. }
  70. } catch (Exception e) {
  71. throw new RuntimeException(e);
  72. }
  73. }
  74. /**
  75. * Create a RPC manager for an RPC target.
  76. *
  77. * @param implementation
  78. * RPC interface implementation for the target
  79. * @param rpcInterface
  80. * RPC interface type
  81. */
  82. public ServerRpcManager(T implementation, Class<T> rpcInterface) {
  83. this.implementation = implementation;
  84. this.rpcInterface = rpcInterface;
  85. }
  86. /**
  87. * Invoke a method in a server side RPC target class. This method is to be
  88. * used by the RPC framework and unit testing tools only.
  89. *
  90. * @param target
  91. * non-null target of the RPC call
  92. * @param invocation
  93. * method invocation to perform
  94. * @throws RpcInvocationException
  95. */
  96. public static void applyInvocation(ClientConnector target,
  97. ServerRpcMethodInvocation invocation)
  98. throws RpcInvocationException {
  99. ServerRpcManager<?> manager = target
  100. .getRpcManager(invocation.getInterfaceName());
  101. if (manager != null) {
  102. manager.applyInvocation(invocation);
  103. } else {
  104. getLogger().log(Level.WARNING,
  105. "RPC call received for RpcTarget {0} ({1}) but the target has not registered any RPC interfaces",
  106. new Object[] { target.getClass().getName(),
  107. invocation.getConnectorId() });
  108. }
  109. }
  110. /**
  111. * Returns the RPC interface implementation for the RPC target.
  112. *
  113. * @return RPC interface implementation
  114. */
  115. protected T getImplementation() {
  116. return implementation;
  117. }
  118. /**
  119. * Returns the RPC interface type managed by this RPC manager instance.
  120. *
  121. * @return RPC interface type
  122. */
  123. public Class<T> getRpcInterface() {
  124. return rpcInterface;
  125. }
  126. /**
  127. * Invoke a method in a server side RPC target class. This method is to be
  128. * used by the RPC framework and unit testing tools only.
  129. *
  130. * @param invocation
  131. * method invocation to perform
  132. */
  133. public void applyInvocation(ServerRpcMethodInvocation invocation)
  134. throws RpcInvocationException {
  135. Method method = invocation.getMethod();
  136. Object[] arguments = invocation.getParameters();
  137. try {
  138. method.invoke(implementation, arguments);
  139. } catch (Exception e) {
  140. throw new RpcInvocationException(
  141. "Unable to invoke method " + invocation.getMethodName()
  142. + " in " + invocation.getInterfaceName(),
  143. e);
  144. }
  145. }
  146. private static Logger getLogger() {
  147. return Logger.getLogger(ServerRpcManager.class.getName());
  148. }
  149. /**
  150. * Returns an RPC proxy for a given client to server RPC interface for the
  151. * given component or extension.
  152. *
  153. * @param connector
  154. * the connector for which to the RPC proxy
  155. * @param rpcInterface
  156. * the RPC interface type
  157. *
  158. * @return a server RPC handler which can be used to invoke RPC methods
  159. * @since 8.0
  160. */
  161. public static <T extends ServerRpc> T getRpcProxy(ClientConnector connector,
  162. final Class<T> rpcInterface) {
  163. @SuppressWarnings("unchecked")
  164. ServerRpcManager<T> rpcManager = (ServerRpcManager<T>) connector
  165. .getRpcManager(rpcInterface.getName());
  166. if (rpcManager == null) {
  167. return null;
  168. }
  169. return rpcManager.getImplementation();
  170. }
  171. }