@Override
  public void handle(RoutingContext context) {
    HttpServerRequest req = context.request();
    String remainingPath = Utils.pathOffset(req.path(), context);

    if (req.method() != HttpMethod.GET && req.method() != HttpMethod.POST) {
      context.next();
    }

    JSONAware json = null;
    try {
      // Check access policy
      requestHandler.checkAccess(
          req.remoteAddress().host(), req.remoteAddress().host(), getOriginOrReferer(req));
      if (req.method() == HttpMethod.GET) {
        json = requestHandler.handleGetRequest(req.uri(), remainingPath, getParams(req.params()));
      } else {
        Arguments.require(
            context.getBody() != null, "Missing body, make sure that BodyHandler is used before");
        // TODO how to get Stream ?
        InputStream inputStream = new ByteBufInputStream(context.getBody().getByteBuf());
        json =
            requestHandler.handlePostRequest(
                req.uri(), inputStream, StandardCharsets.UTF_8.name(), getParams(req.params()));
      }
    } catch (Throwable exp) {
      json =
          requestHandler.handleThrowable(
              exp instanceof RuntimeMBeanException
                  ? ((RuntimeMBeanException) exp).getTargetException()
                  : exp);
    } finally {
      if (json == null)
        json =
            requestHandler.handleThrowable(
                new Exception("Internal error while handling an exception"));

      context
          .response()
          .setStatusCode(getStatusCode(json))
          .putHeader(HttpHeaders.CONTENT_TYPE, contentType)
          .end(json.toJSONString());
    }
  }
  @SuppressWarnings({"PMD.AvoidCatchingThrowable", "PMD.AvoidInstanceofChecksInCatchClause"})
  private void handle(
      ServletRequestHandler pReqHandler, HttpServletRequest pReq, HttpServletResponse pResp)
      throws IOException {
    JSONAware json = null;
    try {
      // Check access policy
      requestHandler.checkAccess(
          pReq.getRemoteHost(), pReq.getRemoteAddr(), getOriginOrReferer(pReq));

      // Remember the agent URL upon the first request. Needed for discovery
      updateAgentDetailsIfNeeded(pReq);

      // Dispatch for the proper HTTP request method
      json = handleSecurely(pReqHandler, pReq, pResp);
    } catch (Throwable exp) {
      json =
          requestHandler.handleThrowable(
              exp instanceof RuntimeMBeanException
                  ? ((RuntimeMBeanException) exp).getTargetException()
                  : exp);
    } finally {
      setCorsHeader(pReq, pResp);

      String callback = pReq.getParameter(ConfigKey.CALLBACK.getKeyValue());
      String answer =
          json != null
              ? json.toJSONString()
              : requestHandler
                  .handleThrowable(new Exception("Internal error while handling an exception"))
                  .toJSONString();
      if (callback != null) {
        // Send a JSONP response
        sendResponse(pResp, "text/javascript", callback + "(" + answer + ");");
      } else {
        sendResponse(pResp, getMimeType(pReq), answer);
      }
    }
  }
  @SuppressWarnings("PMD.AvoidCatchingThrowable")
  private void handle(
      ServletRequestHandler pReqHandler, HttpServletRequest pReq, HttpServletResponse pResp)
      throws IOException {
    JSONAware json = null;
    int code = 200;
    try {
      // Check access policy
      requestHandler.checkClientIPAccess(pReq.getRemoteHost(), pReq.getRemoteAddr());

      // Dispatch for the proper HTTP request method
      json = pReqHandler.handleRequest(pReq, pResp);
      code = requestHandler.extractResultCode(json);
      if (backendManager.isDebug()) {
        backendManager.info("Response: " + json);
      }
    } catch (Throwable exp) {
      JSONObject error = requestHandler.handleThrowable(exp);
      code = (Integer) error.get("status");
      json = error;
    } finally {
      sendResponse(pResp, code, json.toJSONString());
    }
  }