react-web 的 JSONP 類比 POST 請求

來源:互聯網
上載者:User

目的:一份代碼運行三處, ios , android ,web 。通訊底層也共用。react-web使用的http請求是 JSONP,他的特點是: 只能發 get 請求,並且服務端要配合將請求回來的 callback 欄位帶回來。


用戶端實現方案:

將 post 請求內容 base64 放到 url 裡面


var fetch = Platform.OS === 'web'? require('ReactJsonp'): require('ReactFetch');post(url, body) {    let fetchOptions = {        method: 'POST',        deadline: kDeadline,        timeout: kDeadline,        headers: {          'Accept': 'application/json',          'Content-Type': 'application/json',          'uutype': AppGlobal.uutype,          'latitude': AppGlobal.latitude,          'longitude': AppGlobal.longitude,          'token': AppGlobal.userToken,        },        body: JSON.stringify(body)    }    console.log('請求包頭是=='+JSON.stringify(fetchOptions));    if (Platform.OS === 'web') {      // Check if the user set their own params, and if not add a ? to start a list of params      url += url.indexOf('?') === -1 ? '?' : '&';      //把參數放置到 url 裡面      var optString = JSON.stringify(fetchOptions);      var options = new Buffer(optString).toString("base64");      url += 'options='+options;    }    return fetch(url, fetchOptions)        .then(res=>{            try {              console.log('post method res = ' + JSON.stringify(res));              return res.json();            } catch (e) {              return parseError;            }           },          (res)=> {            console.log(`request rejected ${res}`);            throw res;          })    }


服務端方案:

1.支援JSONP

public static void renderJsonporJson(HttpServletResponse response,final String callbackName, final Object object, final String... headers){if (callbackName!=null&&!callbackName.equals("")){renderJsonp(response, callbackName, object, headers);}else {renderJson(response, object, headers);}}

2.支援POST內容放到URL裡面的解碼

流程是:修改 DispatchController 為自訂,然後在自訂類裡面改寫 httpservletrequest ,解碼 url 裡面的 post 內容,然後把內容填寫到新的 request 的 head 和 body 裡面去。


public class CustomDispatch extends DispatcherServlet {@Autowiredprotected void doDispatch(HttpServletRequest request,         HttpServletResponse response) throws Exception {System.out.println("CustomDispatch --------- doDispatch ");String option = request.getParameter("options");if(option != null){//為JSONP請求特殊處理,修改 request 的內容(因為 jsonp 只能 get請求)//System.out.println("CustomDispatch --------- doDispatch options options");HashMap m=new HashMap(request.getParameterMap());//取出參數 base64解碼byte[] b = Encodes.decodeBase64(option);String jsonOption = new String(b); //替換 requestHttpServletRequest req = (HttpServletRequest) request;   HttpRequestChangeable wrapRequest=new HttpRequestChangeable(req,m,jsonOption);     request=wrapRequest; //這是rquest就和本身的request一樣了 }else{                        }super.doDispatch(request, response);}}


package com.defa.tcm.common.customDispatch;import java.io.BufferedReader;  import java.io.IOException;  import java.io.InputStream;  import java.io.InputStreamReader;  import java.nio.charset.Charset;    import javax.servlet.ServletRequest;    public class HttpHelper {      /**      * 擷取請求Body      *      * @param request      * @return      */      public static String getBodyString(ServletRequest request) {          StringBuilder sb = new StringBuilder();          InputStream inputStream = null;          BufferedReader reader = null;          try {              inputStream = request.getInputStream();              reader = new BufferedReader(new InputStreamReader(inputStream, Charset.forName("UTF-8")));              String line = "";              while ((line = reader.readLine()) != null) {                  sb.append(line);              }          } catch (IOException e) {              e.printStackTrace();          } finally {              if (inputStream != null) {                  try {                      inputStream.close();                  } catch (IOException e) {                      e.printStackTrace();                  }              }              if (reader != null) {                  try {                      reader.close();                  } catch (IOException e) {                      e.printStackTrace();                  }              }          }          return sb.toString();      }  }  


@SuppressWarnings("unchecked")  public class HttpRequestChangeable extends HttpServletRequestWrapper {   private Map params;  private final byte[] body;  private final HashMap headersHash;private final List headKey;      public HttpRequestChangeable(HttpServletRequest request, Map newParams,String postContent) {          super(request);                  this.params = newParams;                JSONObject jsonObj = JSONObject.fromObject(postContent); String bodyStr = jsonObj.getString("body");String headers = jsonObj.getString("headers");JSONObject jsonHead = JSONObject.fromObject(headers);headersHash = new HashMap();parserToMap(headers,headersHash );                //列印 head//        Enumeration e = request.getHeaderNames()   ;    //         while(e.hasMoreElements()){    //             String name = (String) e.nextElement();    //             String value = request.getHeader(name);    //             System.out.println(name+" = "+value);    //                 //         } //設定 head key        headKey = new ArrayList();    Iterator keys=jsonHead.keys();      while(keys.hasNext()){          String key=(String) keys.next();          if(key != "body"){        headKey.add(key);        }            }                          //設定 head 和 body        body = bodyStr.getBytes(Charset.forName("UTF-8")); //        body = HttpHelper.getBodyString(request).getBytes(Charset.forName("UTF-8"));              }        public Map getParameterMap() {          return params;      }        public Enumeration getParameterNames() {          Vector l = new Vector(params.keySet());          return l.elements();      }        public String[] getParameterValues(String name) {          Object v = params.get(name);          if (v == null) {              return null;          } else if (v instanceof String[]) {              return (String[]) v;          } else if (v instanceof String) {              return new String[] { (String) v };          } else {              return new String[] { v.toString() };          }      }        public String getParameter(String name) {          Object v = params.get(name);          if (v == null) {              return null;          } else if (v instanceof String[]) {              String[] strArr = (String[]) v;              if (strArr.length > 0) {                  return strArr[0];              } else {                  return null;              }          } else if (v instanceof String) {              return (String) v;          } else {              return v.toString();          }      }          @Override      public BufferedReader getReader() throws IOException {          return new BufferedReader(new InputStreamReader(getInputStream()));      }        @Override      public ServletInputStream getInputStream() throws IOException {            final ByteArrayInputStream bais = new ByteArrayInputStream(body);            return new ServletInputStream() {              @Override              public int read() throws IOException {                  return bais.read();              }@Overridepublic boolean isFinished() {if(bais.available() == 0){return true;}return false;}@Overridepublic boolean isReady() {if(bais.available() > 0){return true;}return false;}@Overridepublic void setReadListener(ReadListener readListener) {// TODO Auto-generated method stub}          };      }        @Override      public String getHeader(String name) {    return (String) headersHash.get(name);//        return super.getHeader(name);      }        @Override      public Enumeration<String> getHeaderNames() {    return new Enumeration(){    int count = headKey.size();    int curIndex = 0;@Overridepublic boolean hasMoreElements() {if(curIndex < count){return true;}return false;}@Overridepublic Object nextElement() {if(curIndex < count){Object res = headKey.get(curIndex++);return res;}return null;}        };//        return super.getHeaderNames();      }        @Override      public Enumeration<String> getHeaders(final String name) {      return new Enumeration(){    int count = 1;    int curIndex = 0;@Overridepublic boolean hasMoreElements() {if(curIndex < count){return true;}return false;}@Overridepublic Object nextElement() {if(curIndex < count){curIndex++;return headersHash.get(name);}return null;}        };//        return super.getHeaders(name);      }          //public static Map parserToMap(String s,Map initMap){      Map map= initMap;    if(map == null){    map = new HashMap();    }          JSONObject json=JSONObject.fromObject(s);      Iterator keys=json.keys();      while(keys.hasNext()){          String key=(String) keys.next();          String value=json.get(key).toString();          if(value.startsWith("{")&&value.endsWith("}")){              map.put(key, parserToMap(value,null));          }else{              map.put(key, value);          }        }      return map;  }  public static final byte[] readBytes(InputStream is, int contentLen) {if (contentLen > 0) {int readLen = 0;int readLengthThisTime = 0;byte[] message = new byte[contentLen];try {while (readLen != contentLen) {readLengthThisTime = is.read(message, readLen, contentLen - readLen);if (readLengthThisTime == -1) {// Should not happen.break;}readLen += readLengthThisTime;}return message;} catch (IOException e) {// Ignore// e.printStackTrace();}}return new byte[] {};}    } 










相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.