Package com.baidu.qa.service.test.client

Source Code of com.baidu.qa.service.test.client.JsonRpcServiceClientImpl

package com.baidu.qa.service.test.client;

import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.lang.reflect.Method;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLConnection;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.atomic.AtomicInteger;

import net.sf.json.JSONObject;

import org.apache.log4j.Logger;

import com.baidu.gson.Gson;
import com.baidu.gson.GsonBuilder;
import com.baidu.gson.JsonElement;
import com.baidu.gson.JsonObject;
import com.baidu.qa.service.test.dto.CaseData;
import com.baidu.qa.service.test.dto.Config;
import com.baidu.qa.service.test.dto.Constant;
import com.baidu.rpc.McpackProcessor;
import com.baidu.rpc.exception.ExceptionHandler;
import com.baidu.rpc.exception.InternalErrorException;
import com.baidu.rpc.exception.JsonRpcException;
import com.baidu.rpc.exception.ParseErrorException;
import com.baidu.rpc.exception.ServerErrorException;

public class JsonRpcServiceClientImpl implements ServiceInterfaceClient {
 
  private static Logger log = Logger.getLogger(JsonRpcServiceClientImpl.class);
 
  final static Gson gson = new GsonBuilder().serializeNulls()
      .disableHtmlEscaping().serializeSpecialFloatingPointValues()
      .create();

  private static final String encoding = "gbk";

  protected AtomicInteger counter = new AtomicInteger();
 
  protected ExceptionHandler exceptionHandler = new ExceptionHandler();

//  private String url;

  private int _connectTimeout = 30000;

  private int _readTimeout = 30000;

  public Object invokeServiceMethod(CaseData casedata, Config config) {
   
    //如果是tpl文件,进行替换和重新set input
    if(casedata.getInputFile().getName().endsWith(Constant.FILE_TYPE_TPL)){
      casedata.setInputFile(casedata.getVarGen().processTemplate(casedata.getInputFile()));
      casedata.setInput();
    }
   
    String input = casedata.getInputJson();
   
    String action = casedata.getAction();
   
    String [] serviceAndMethod = getSmFromAction(action);
   
    String host = "";
 
   
      host=config.getHost();
   
   
    String actual = null;
   
    try {
      actual = invoke(host, serviceAndMethod, input);
    } catch (Throwable t) {
      log.error(t.getMessage(), t);
    }
    return actual;
  }
 
 
 
  /**
   * action : XxxApi/xxx
   * @param action
   * @return
   */
  private String[] getSmFromAction(String action) {
    return action.split("/");
  }

  /*
   * (non-Javadoc)
   *
   * @see com.baidu.rpc.client.RpcProxyBase#deserialize(byte[])
   */
  protected JsonElement deserialize(byte[] req) throws ParseErrorException {
    return  new McpackProcessor().deserialize(encoding, req);
  }

  /*
   * (non-Javadoc)
   *
   * @see
   * com.baidu.rpc.client.RpcProxyBase#serialize(com.google.gson.JsonElement)
   */
  protected byte[] serialize(JsonElement res) throws ParseErrorException {
    return  new McpackProcessor().serialize(encoding, res);
  }


  public String invoke(String host, String[] serviceAndMethod, String input)
      throws Throwable {
    try {
      int id = counter.getAndIncrement();
      JsonElement request = makeRequest(id, serviceAndMethod, input);
      byte[] reqBytes = serialize(request);
      // log.debug("request bytes size is " + reqBytes.length);
     
      String url = host + serviceAndMethod[0];
     
      log.info("input: " + input);
      log.info("url: " + url);
     
      HttpURLConnection connection = (HttpURLConnection) new URL(url)
          .openConnection();
      if (_connectTimeout > 0) {
        connection.setConnectTimeout(_connectTimeout);
      }
      if (_readTimeout > 0) {
        connection.setReadTimeout(_readTimeout);
      }
      sendRequest(reqBytes, connection);
      byte[] resBytes = null;
      resBytes = readResponse(connection);
      JsonElement resJson = deserialize(resBytes);
//      return parseResult(id, resJson, method);
      return resJson.toString();
    } catch (IOException e) {
      throw new InternalErrorException(e);
    }
  }

  /**
   * 读取服务器返回的信息
   *
   * @param connection
   * @return 读取到的数据
   * @throws IOException
   * @throws JsonRpcException
   */
  protected byte[] readResponse(URLConnection connection)
      throws JsonRpcException {
    byte[] resBytes;
    InputStream in = null;
    HttpURLConnection httpconnection = (HttpURLConnection) connection;
    try {
      if (httpconnection.getResponseCode() == HttpURLConnection.HTTP_OK) {
        in = httpconnection.getInputStream();
      } else {
        if (httpconnection.getContentType().equals(contentType())
            && httpconnection.getErrorStream() != null) {
          in = httpconnection.getErrorStream();
        } else {
          in = httpconnection.getInputStream();
        }
      }
      int len = httpconnection.getContentLength();
      if (len <= 0) {
        throw new InternalErrorException("no response to get.");
      }
      resBytes = new byte[len];
      int offset = 0;
      while (offset < resBytes.length) {
        int bytesRead = in.read(resBytes, offset, resBytes.length
            - offset);
        if (bytesRead == -1)
          break; // end of stream
        offset += bytesRead;
      }
      if (offset <= 0) {
        throw new InternalErrorException("there is no service to "
            + connection.getURL());
      }
      // log.debug("response bytes size is " + offset);
    } catch (IOException e) {
      throw new InternalErrorException(e);
    } finally {
      if (in != null) {
        try {
          in.close();
        } catch (IOException e) {
          throw new InternalErrorException(e);
        }
      }
    }
    return resBytes;
  }

  /**
   * 向服务器发送信息
   *
   * @param reqBytes
   * @param connection
   * @throws IOException
   */

  protected void sendRequest(byte[] reqBytes, URLConnection connection) {
    HttpURLConnection httpconnection = (HttpURLConnection) connection;
    OutputStream out = null;
    try {
      httpconnection.setRequestMethod("POST");
      httpconnection.setUseCaches(false);
      httpconnection.setDoInput(true);
      httpconnection.setDoOutput(true);
      httpconnection.setRequestProperty("Content-Type", contentType()
          + ";charset=" + encoding);
      httpconnection.setRequestProperty("Content-Length", ""
          + reqBytes.length);
      httpconnection.connect();
      out = httpconnection.getOutputStream();
      out.write(reqBytes);
    } catch (Exception e) {
      throw new InternalErrorException(e);
    } finally {
      if (out != null) {
        try {
          out.close();
        } catch (IOException e) {
          throw new InternalErrorException(e);
        }
      }
    }
  }

  /**
   * 组装rpc数据报
   *
   * @param serviceAndMethod
   * @param input
   * @return 生成的请求数据
   * @throws ParseErrorException
   */
  protected JsonElement makeRequest(int id, String[] serviceAndMethod, String input)
      throws ParseErrorException {
    String name = serviceAndMethod[1];
   
    StringBuilder sb = new StringBuilder();
   
    sb.append("{\"jsonrpc\":\"2.0\",\"method\":\"").append(name).append("\",\"params\":[");
   
    if (input != null) {
      sb.append(input);
    } else {
      sb.append("{}");
    }
   
    sb.append("],\"id\":\"").append(id).append("\"}");
   
    log.info(sb);
   
//    Map<String, Object> all = new HashMap<String, Object>();
   
    JSONObject a = JSONObject.fromObject(sb.toString());
   
    return new Gson().toJsonElement(a);
  }

  /**
   * 处理接受到的rpc数据报
   *
   * @param ele
   * @param method
   * @return 调用的返回值
   * @throws Exception
   */
  @Deprecated
  protected Object parseResult(int id, JsonElement ele, Method method)
      throws Exception {
    JsonObject res = (JsonObject) ele;
    if (!res.get("jsonrpc").getAsString().equals("2.0")) {
      throw new InternalErrorException();
    }
    JsonElement result = res.get("result");
    if (result != null) {
      if (res.get("id").getAsInt() != id) {
        throw new InternalErrorException("no id in response");
      } else {
        return gson.fromJson(result, method.getGenericReturnType());
      }
    } else {
      JsonElement e = res.get("error");
      if (e != null) {
        JsonRpcException jre = exceptionHandler.deserialize(e);
        if (jre instanceof ServerErrorException) {
          String msg = jre.getMessage();
          Class<?>[] exp_types = method.getExceptionTypes();
          for (Class<?> exp_type : exp_types) {
            if (msg.equals(exp_type.getSimpleName())) {
              Exception custom_exp = (Exception) exp_type
                  .newInstance();
              custom_exp.initCause(jre.getCause());
              throw custom_exp;
            }
          }
        }
        throw jre;
      } else {
        throw new InternalErrorException("no error or result returned");
      }
    }
  }
 
  protected String contentType() {
    return "application/baidu.mcpack-rpc";
  }

  public Object clone() throws CloneNotSupportedException {
    return super.clone();
  }

}
TOP

Related Classes of com.baidu.qa.service.test.client.JsonRpcServiceClientImpl

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.