Ejemplo n.º 1
0
  private void handleJsonResponses() {
    ServletRequestInfo info = getServletRequestInfo();

    if (info.currentJsonRequest == null) return;

    info.response.setContentType("application/json");
    info.response.setCharacterEncoding("UTF-8");
    String result;
    try {
      if (info.jsonResponses.size() == 0) {
        ServletOutputStream out = info.getOutputStream();
        out.close();
        out.flush();
        return;
      }
      if (!info.isBatchRequest) {
        result = (new Gson()).toJson(info.jsonResponses.get(0));
      } else {
        result = (new Gson()).toJson(info.jsonResponses);
      }

      PrintWriter writer = new PrintWriter(info.getOutputStream());
      writer.print(result);
      writer.close();
      writer.flush();

    } catch (Exception e) {
      e.printStackTrace();
    }
  }
Ejemplo n.º 2
0
  private void handleArrayOfJsonRequests(
      PeekableInputStream inputStream, HttpServletResponse response) throws IOException {
    try {
      JsonRpcRequestModel[] jsonRequests;
      String streamString = IOUtils.toString(inputStream, "UTF-8");

      ServletRequestInfo info = getServletRequestInfo();
      /*If first character is { then it is a single request. We add it to the array jsonRequests and continue*/
      if (streamString.charAt(0) == '{') {
        // TODO:CHeck parse error for this
        JsonRpcRequestModel req = (new Gson()).fromJson(streamString, JsonRpcRequestModel.class);
        jsonRequests = new JsonRpcRequestModel[] {req};
        info.isBatchRequest = false;
      } else {
        jsonRequests = (new Gson()).fromJson(streamString, JsonRpcRequestModel[].class);
        info.isBatchRequest = true;
      }

      /* we loop through each request, get results or check error and add repsonses to an array*/
      for (int i = 0; i < jsonRequests.length; i++) {
        info.currentJsonRequest = jsonRequests[i];

        /* Check to see if JSON-RPC protocol is 2.0*/
        if (info.currentJsonRequest.jsonrpc == null
            || !info.currentJsonRequest.jsonrpc.equals(JSONRPC_VERSION)) {
          sendJsonError(JSON_RPC_PROTOCOL_ERROR_MESSAGE, info.currentJsonRequest.jsonrpc);
          continue;
        }
        /*Check if ID is a number and if so it has not fractional numbers*/
        else if (info.currentJsonRequest.id instanceof Number) {
          Number number = (Number) info.currentJsonRequest.id;
          if (number.intValue() != number.doubleValue()) {
            sendJsonError(JSON_RPC_ID_ERROR_MESSAGE, info.currentJsonRequest.id);
            continue;
          }
          info.currentJsonRequest.id = number.intValue();
        }

        /*Check if Method exists*/
        if (!methodMap.containsKey(info.currentJsonRequest.method)) {
          sendJsonError(JSON_RPC_METHOD_ERROR_MESSAGE, info.currentJsonRequest.method);
          continue;
        }

        invokeMethod(info.currentJsonRequest.method, info.currentJsonRequest.params);
      }

    } catch (JsonParseException e) {
      sendError(e, JSON_RPC_PARSE_ERROR_MESSAGE);
    }
  }
Ejemplo n.º 3
0
  @SuppressWarnings("unchecked")
  private void handleServletRequest(HttpServletRequest request, HttpServletResponse response)
      throws IOException, ServletException {
    try {
      ServletRequestInfo info = setServletRequestInfo(request, response);

      if (request.getMethod().equals("GET")) {
        List<String> urlParamNames = Collections.list(request.getParameterNames());

        HashMap<String, String> params = new HashMap<String, String>();

        for (String paramName : urlParamNames)
          params.put(paramName, request.getParameter(paramName));
        JsonRpcRequestModel json = new JsonRpcRequestModel();
        json.jsonrpc = JSONRPC_VERSION;
        json.id = "";
        json.method = params.remove(METHOD);
        json.params = params;

        info.currentJsonRequest = json;
        invokeMethod(json.method, params);
      } else // post
      {
        try {
          String methodName;
          Object methodParams;
          if (info.inputStream.peek() == '[' || info.inputStream.peek() == '{') // json
          {
            handleArrayOfJsonRequests(info.inputStream, response);
          } else // AMF3
          {
            ASObject obj = (ASObject) deserializeAmf3(info.inputStream);
            methodName = (String) obj.get(METHOD);
            methodParams = obj.get(PARAMS);
            info.streamParameterIndex = (Number) obj.get(STREAM_PARAMETER_INDEX);
            invokeMethod(methodName, methodParams);
          }
        } catch (IOException e) {
          sendError(e, null);
        } catch (Exception e) {
          sendError(e, null);
        }
      }
      handleJsonResponses();
    } finally {
      removeServletRequestInfo();
    }
  }
Ejemplo n.º 4
0
  private void sendError(Throwable exception, String moreInfo) throws IOException {
    if (exception instanceof InvocationTargetException) exception = exception.getCause();

    // log errors
    exception.printStackTrace();

    String message;
    if (exception instanceof RuntimeException) message = exception.toString();
    else message = exception.getMessage();

    if (moreInfo != null) message += "\n" + moreInfo;

    System.err.println("Serializing ErrorMessage: " + message);

    ServletRequestInfo info = getServletRequestInfo();
    if (info.currentJsonRequest == null) {
      ServletOutputStream servletOutputStream = info.getOutputStream();
      ErrorMessage errorMessage = new ErrorMessage(new MessageException(message));
      errorMessage.faultCode = exception.getClass().getSimpleName();
      serializeCompressedAmf3(errorMessage, servletOutputStream);
    } else {
      sendJsonError(message, null);
    }
  }
Ejemplo n.º 5
0
  /**
   * @param methodName The name of the function to invoke.
   * @param methodParams A Map, List, or Array of input parameters for the method. Values will be
   *     cast to the appropriate types if necessary.
   */
  private void invokeMethod(String methodName, Object methodParams) throws IOException {
    ServletRequestInfo info = getServletRequestInfo();
    if (!methodMap.containsKey(methodName) || methodMap.get(methodName) == null) {
      sendError(
          new IllegalArgumentException(String.format("Method \"%s\" not supported.", methodName)),
          null);
      return;
    }

    if (methodParams == null) methodParams = new Object[0];

    if (methodParams instanceof Map)
      methodParams = getParamsFromMap(methodName, (Map<?, ?>) methodParams);

    if (methodParams instanceof List<?>) methodParams = ((List<?>) methodParams).toArray();

    if (info.streamParameterIndex != null) {
      int index = info.streamParameterIndex.intValue();
      if (index >= 0) ((Object[]) methodParams)[index] = info.inputStream;
    }

    Object[] params = (Object[]) methodParams;

    // get method by name
    ExposedMethod exposedMethod = methodMap.get(methodName);
    if (exposedMethod == null) {
      sendError(new IllegalArgumentException("Unknown method: " + methodName), null);
      return;
    }

    // cast input values to appropriate types if necessary
    Class<?>[] expectedArgTypes = exposedMethod.method.getParameterTypes();
    if (expectedArgTypes.length == params.length) {
      for (int index = 0; index < params.length; index++) {
        params[index] = cast(params[index], expectedArgTypes[index]);
      }
    }

    // prepare to output the result of the method call
    long startTime = System.currentTimeMillis();

    // Invoke the method on the object with the arguments
    try {
      Object result = exposedMethod.method.invoke(exposedMethod.instance, params);

      if (info.currentJsonRequest == null) // AMF3
      {
        if (exposedMethod.method.getReturnType() != void.class) {
          ServletOutputStream servletOutputStream = info.getOutputStream();
          serializeCompressedAmf3(result, servletOutputStream);
        }
      } else // json
      {
        Object id = info.currentJsonRequest.id;
        /* If ID is empty then it is a notification, we send nothing back */
        if (id != null) {
          JsonRpcResponseModel responseObj = new JsonRpcResponseModel();
          responseObj.jsonrpc = "2.0";
          responseObj.result = result;
          responseObj.id = id;
          info.jsonResponses.add(responseObj);
        }
      }

    } catch (InvocationTargetException e) {
      System.err.println(methodToString(methodName, params));
      sendError(e, null);
    } catch (IllegalArgumentException e) {
      String moreInfo =
          "Expected: "
              + formatFunctionSignature(methodName, expectedArgTypes, exposedMethod.paramNames)
              + "\n"
              + "Received: "
              + formatFunctionSignature(methodName, params, null);

      sendError(e, moreInfo);
    } catch (Exception e) {
      System.err.println(methodToString(methodName, params));
      sendError(e, null);
    }

    long endTime = System.currentTimeMillis();
    // debug
    if (endTime - startTime >= debugThreshold)
      System.out.println(
          String.format("[%sms] %s", endTime - startTime, methodToString(methodName, params)));
  }