基于HttpUrlConnection的简单封装SimpleHttp

来源:互联网 发布:金铅笔网络运营 编辑:程序博客网 时间:2024/05/17 07:51

1、封装前准备

1.1、定义一个请求方法的枚举类型
package com.gau.simplehttp.http;public enum HttpMethod {    GET, POST}
1.2、定义一个响应结果实体,用于接收服务器返回的数据
package com.gau.simplehttp.http;public class Response {    private final int code;    private final String message;    private final String method;    private final String contentType;    private final int contentLength;    private final String body;    public Response(Builder builder) {        this.code = builder.code;        this.message = builder.message;        this.method = builder.method;        this.contentType = builder.contentType;        this.contentLength = builder.contentLength;        this.body = builder.body;    }    public int getCode() {        return code;    }    public String getMessage() {        return message;    }    public String getMethod() {        return method;    }    public String getContentType() {        return contentType;    }    public int getContentLength() {        return contentLength;    }    public boolean isSuccessful() {        return this.code >= 200 && this.code < 300;    }    public String getBody() {        return body;    }    public static class Builder {        private int code;        private String message;        private String method;        private String contentType;        private int contentLength;        private String body;        public Builder code(int code) {            this.code = code;            return this;        }        public Builder message(String message) {            this.message = message;            return this;        }        public Builder method(String method) {            this.method = method;            return this;        }        public Builder contentType(String contentType) {            this.contentType = contentType;            return this;        }        public Builder contentLength(int contentLength) {            this.contentLength = contentLength;            return this;        }        public Builder body(String body) {            this.body = body;            return this;        }        public Response build() {            return new Response(this);        }    }}
1.3、定义一个请求回调,其中Response为自己定义的响应结果
public interface HttpCallback {    void onComplete(Response response);    void onError(Throwable e);}

2、封装ing

2.1、请求体的封装
package com.gau.simplehttp.http;import java.io.BufferedReader;import java.io.IOException;import java.io.InputStream;import java.io.InputStreamReader;import java.net.HttpURLConnection;import java.net.URL;import java.util.ArrayList;import java.util.List;public class Request {    private final static int CONNECT_TIME_OUT_MILLISECOND = 10000;    private final static int READ_TIME_OUT_MILLISECOND = 20000;    private String url;    private List<String> params;    private List<String> headers;    private String string;    private HttpMethod method;    private HttpURLConnection connection;    private static HttpCallback mHttpCallback;    private Request(Builder builder) {        this.url = builder.url;        this.params = builder.params;        this.headers = builder.headers;        this.method = builder.method;        this.string = builder.string;    }    public static Request newRequest(Builder builder) {        return newRequest(builder, null);    }    public static Request newRequest(Builder builder, HttpCallback httpCallback) {        mHttpCallback = httpCallback;        return new Request(builder);    }    /*     * 异步请求     */    public void executeAsync() {        HttpAsyncTask asyncTask = new HttpAsyncTask(this, connection, mHttpCallback);        asyncTask.execute();    }    /*     * 同步请求     */    public Response execute() throws IOException {        if (method == HttpMethod.POST) {            post();        } else {            get();        }        return response(connection);    }    /*     * get请求     */    private void get() throws IOException {        URL requestUrl = new URL(getUrl(url));        connection = (HttpURLConnection) requestUrl.openConnection();        connection.setRequestMethod(String.valueOf(method));        connection.setConnectTimeout(CONNECT_TIME_OUT_MILLISECOND);        connection.setReadTimeout(READ_TIME_OUT_MILLISECOND);        connection.setDoInput(true);        connection.setUseCaches(false);        connectHeaders();        connection.connect();    }    /*     * get请求拼接url     */    private String getUrl(String url) {        StringBuilder sb = new StringBuilder();        sb.append(url).append("?");        for (int i = 0; i < params.size(); i += 2) {            sb.append(params.get(i));            sb.append("=");            sb.append(params.get(i + 1));            sb.append("&");        }        sb.deleteCharAt(sb.length() - 1);        return sb.toString();    }    /*     * post请求     */    private void post() throws IOException {        URL requestUrl = new URL(url);        connection = (HttpURLConnection) requestUrl.openConnection();        connection.setRequestMethod(String.valueOf(method));        connection.setConnectTimeout(CONNECT_TIME_OUT_MILLISECOND);        connection.setReadTimeout(READ_TIME_OUT_MILLISECOND);        connection.setDoInput(true);        connection.setDoOutput(true);        connection.setUseCaches(false);        connectHeaders();        connection.connect();        postBody();    }    /*     * post请求上传数据     */    private void postBody() throws IOException {        postForm();        postString();    }    /*     * 上传表单     */    private void postForm() throws IOException {        if (params != null && params.size() > 0) {            StringBuilder sb = new StringBuilder();            for (int i = 0; i < params.size(); i += 2) {                sb.append(params.get(i));                sb.append("=");                sb.append(params.get(i + 1));                sb.append("&");            }            sb.deleteCharAt(sb.length() - 1);            connection.getOutputStream().write(sb.toString().getBytes("GBK"));        }    }    /*     * 上传字符串,如json字符串     */    private void postString() throws IOException {        if (string != null && !string.isEmpty()) {            connection.getOutputStream().write(string.getBytes("GBK"));        }    }    /*     * 设置请求头     */    private void connectHeaders() {        if (headers != null && headers.size() > 0) {            for (int i = 0; i < headers.size(); i += 2) {                connection.setRequestProperty(headers.get(i), headers.get(i + 1));            }        }    }    /*     * 获取响应结果     */    private Response response(HttpURLConnection connection) throws IOException {        Response resp = new Response.Builder()                .code(connection.getResponseCode())                .message(connection.getResponseMessage())                .method(connection.getRequestMethod())                .contentType(connection.getContentType())                .contentLength(connection.getContentLength())                .body(getResponseBody(connection.getInputStream()))                .build();        connection.disconnect();        return resp;    }    /*     * 获取响应的数据     */    private String getResponseBody(InputStream stream) {        StringBuilder sb = new StringBuilder();        BufferedReader br = new BufferedReader(new InputStreamReader(stream));        String line;        try {            while ((line = br.readLine()) != null) {                sb.append(line).append("\r\n");            }            br.close();        } catch (IOException e) {            e.printStackTrace();        }        return sb.toString();    }    public static class Builder {        private String url;        private List<String> params = new ArrayList<>();        private List<String> headers = new ArrayList<>();        private HttpMethod method = HttpMethod.GET;        private String string;        public Builder url(String url) {            if (url == null || url.isEmpty()) {                throw new IllegalArgumentException("url can not be null or empty");            }            this.url = url;            return this;        }        public Builder method(HttpMethod method) {            this.method = method;            return this;        }        public Builder params(String key, String value) {            params.add(key);            params.add(value);            return this;        }        public Builder headers(String key, String values) {            headers.add(key);            headers.add(values);            return this;        }        public Builder string(String string) {            this.string = string;            return this;        }        public Request build() {            return new Request(this);        }    }}

Request包含同步请求和异步请求两种方式,其中异步请求采用的是AsyncTask实现。

2.2、异步的实现
package com.gau.simplehttp.http;import android.os.AsyncTask;import java.io.IOException;import java.net.HttpURLConnection;public class HttpAsyncTask extends AsyncTask<Void, Void, Response> {    private Request request;    private HttpURLConnection connection;    private HttpCallback httpCallback;    private Exception exception;    public HttpAsyncTask(Request request, HttpURLConnection connection, HttpCallback httpCallback) {        this.connection = connection;        this.request = request;        this.httpCallback = httpCallback;    }    @Override    protected Response doInBackground(Void... params) {        try {            if (request != null) {                return request.execute();            }        } catch (IOException e) {            if (connection != null) {                connection.disconnect();            }            exception = e;        }        return null;    }    @Override    protected void onPostExecute(Response response) {        super.onPostExecute(response);        if (response == null) {            if (httpCallback != null) {                if (exception != null) {                    httpCallback.onError(exception);                } else {                    httpCallback.onError(new Exception("UnKnown Exception"));                }            }        } else {            if (httpCallback != null) {                httpCallback.onComplete(response);            }        }    }}

ps: 回调的结果是直接回调到主线程中,所以可以在回调方法里直接对UI进行操作。

3、测试代码

// 同步请求new Thread(new Runnable() {    @Override    public void run() {        Request.Builder builder = new Request.Builder().url("https://www.baidu.com");        Request request = Request.newRequest(builder);        try {            Response response = request.execute();            if (response != null) {                if (response.isSuccessful()) {                    Log.e(TAG, "response is success:" + response.getBody());                } else {                    Log.e(TAG, "response is fail:" + response.getBody());                }            }        } catch (IOException e) {            e.printStackTrace();        }    }}).start();// 异步请求Request.Builder build = new Request.Builder()                            .url("http://10.0.3.2:8080/TestProject/TestServlet")                            .method(HttpMethod.POST)                            .headers("User-Agent", "guochao-1.0")                            .params("param1", "hello world")                            .params("param2","bye bye world")                            .string("{\"json\":\"string\"}");Request.newRequest(build, new HttpCallback() {    @Override    public void onComplete(Response response) {        Log.e(TAG, "onComplete/response:" + response.getBody());    }    @Override    public void onError(Throwable e) {        Log.e(TAG, "onError:" + e.getMessage());    }}).executeAsync();

请求的参数可以通过调用builder.params("","")传递,请求头通过builder.headers("","")设置,最后通过request.execute()同步发送请求或request.executeAsync()异步发起请求。

github地址

0 0
原创粉丝点击