新手入门 安卓电商系统基于OkHttp3的请求封装

最近有时间闲下来做一些以前工作的复习,翻到了上次的电商项目的代码,想起了那段用别人封装不顺手,自己又不会封装的痛苦时期,所以我决定把自己最终的劳动成果记录下来,方便以后的自己来看一看现在的自己有多蠢2333.

上次是我第一次做前后端的交互,我对交互的印象只有get ,post,put,delete四种请求,但是并不知道应该怎样具体实现它们,在登录注册以及表单提交中大多使用的是post请求,所以我新建了一个接口类管理这几种数据的提交方式


public interface IHttpClient {

    IResponse get(IRequest request);

    /**

    * json类型的post

*

    * @param request

    * @return

    */

    IResponse post(IRequest request);

    /**

    * 表单类型的post

*

    * @param request

    * @return

    */

    IResponse put(IRequest request);

    IResponse delete(IRequest request);

    IResponse upload_image_post(IRequest request, Map<String, Object> map, File file);

}

另外新建IRequest类指定请求的方式,请求头等等

public interface IRequest {

    public static final String POST = "POST";
    public static final String GET = "GET";
    public static final String PUT = "PUT";
    public static final String DELETE = "DELETE";

    /**
     * 请求方式
     *
     * @param method
     */
    void setMethod(String method);

    /**
     * 指定请求头
     *
     * @param key
     * @param value
     */
    void setHeader(String key, String value);

    /**
     * 指定请求信息
     *
     * @param key
     * @param value
     */
    void setBody(String key, Object value);

    /**
     * 提供给执行库请求行URL
     *
     * @return
     */
    String getUrl();

    /**
     * 提供给执行库请求行URL
     *
     * @return
     */
    Map<String, String> getHeader();

    /**
     * 请求体
     *
     * @return
     */
    String getBody();
}

使用Gson组装请求参数

public class RequestImpl implements IRequest {

    private String method = "POST";
    private String url;
    private Map<String, String> header;
    private Map<String, Object> body;

    public RequestImpl(String url) {
        /**
         * 初始化公共参数和头部信息
         */
        this.url = url;
        header = new HashMap();
        body = new HashMap<>();
    }

    @Override
    public void setMethod(String method) {
        this.method = method;
    }

    @Override
    public void setHeader(String key, String value) {
        header.put(key, value);
    }

    @Override
    public void setBody(String key, Object value) {
        body.put(key, value);
    }

    @Override
    public String getUrl() {
        if (GET.equals(method)) {
            // 组装post请求参数
            for (String key : body.keySet()) {
                url = url.replace("${" + key + "}", body.get(key).toString());
            }
        }
        return url;
    }

    @Override
    public Map<String, String> getHeader() {
        return header;
    }

    @Override
    public String getBody() {
        // 组装post请求参数
        if (body != null) {
            return new Gson().toJson(this.body, HashMap.class);
        } else {
            return "{}";
        }
    }
}

最后新建请求方法实现类,将四种请求全部重写,然后添加公共执行方法Execute

public class OkHttpClientImpl implements IHttpClient {

    OkHttpClient mOkHttpClient = new OkHttpClient.Builder().build();

    @Override
    public IResponse get(IRequest request) {
        /**
         * 解析业务参数
         */
        request.setMethod(IRequest.GET);
        Map<String, String> header = request.getHeader();
        Request.Builder builder = new Request.Builder();
        for (String key : header.keySet()) {
            builder.header(key, header.get(key));
        }
        builder.url(request.getUrl()).get();
        Request okRequest = builder.build();
        return execute(okRequest);

    }

    /**
     * POST请求
     *
     * @param request
     * @return
     */
    @Override
    public IResponse post(IRequest request) {
        request.setMethod(IRequest.POST);
        MediaType mediaType = MediaType.parse("application/json; charset=utf-8");
        RequestBody requestBody = RequestBody.create(mediaType, request.getBody().toString());

        Map<String, String> header = request.getHeader();
        Request.Builder builder = new Request.Builder();
        for (String key : header.keySet()) {
            builder.header(key, header.get(key));
        }
        builder.url(request.getUrl())
                .post(requestBody);
        Request okRequest = builder.build();
        return execute(okRequest);
    }

    /**
     * PUT请求
     *
     * @param request
     * @return
     */
    @Override
    public IResponse put(IRequest request) {
        request.setMethod(IRequest.PUT);
        MediaType mediaType = MediaType.parse("application/json; charset=utf-8");
        RequestBody requestBody = RequestBody.create(mediaType, request.getBody().toString());

        Map<String, String> header = request.getHeader();
        Request.Builder builder = new Request.Builder();
        for (String key : header.keySet()) {
            builder.header(key, header.get(key));
        }
        builder.url(request.getUrl())
                .put(requestBody);
        Request okRequest = builder.build();
        return execute(okRequest);

    }

    /**
     * GET请求
     *
     * @param request
     * @return
     */
    @Override
    public IResponse delete(IRequest request) {
        request.setMethod(IRequest.DELETE);
        Map<String, String> header = request.getHeader();
        Request.Builder builder = new Request.Builder();
        for (String key : header.keySet()) {
            builder.header(key, header.get(key));
        }
        builder.url(request.getUrl())
                .delete(null);
        Request okRequest = builder.build();
        return execute(okRequest);
    }

    /**
     * 文件上传
     *
     * @param request
     * @param map
     * @param file
     * @return
     */
    @Override
    public IResponse upload_image_post(IRequest request, Map<String, Object> map, File file) {
        /**
         *  实现文件上传
         */
        request.setMethod(IRequest.POST);
        MediaType MEDIA_TYPE_IMAGE = MediaType.parse("image/*");
        MultipartBody.Builder requestBody = new MultipartBody
                .Builder().setType(MultipartBody.FORM);
        if (file != null) {
            requestBody.addFormDataPart("image", file.getName(),
                    RequestBody.create(MEDIA_TYPE_IMAGE, file));
        }
        if (map != null) {
            // map 里面是请求中所需要的 key 和 value
            for (Map.Entry entry : map.entrySet()) {
                requestBody.addFormDataPart(valueOf(entry.getKey()), valueOf(entry.getValue()));
            }
        }
        Map<String, String> header = request.getHeader();
        Request.Builder builder = new Request.Builder();
        for (String key : header.keySet()) {
            builder.header(key, header.get(key));
        }
        builder.url(request.getUrl())
                .post(requestBody.build());
        Request okRequest = builder.build();
        return execute(okRequest);
    }

    /**
     * 公共Execute方法
     *
     * @param request
     * @return
     */
    private IResponse execute(Request request) {
        ResponseImpl commonResponse = new ResponseImpl();

        try {
            Response response = mOkHttpClient.newCall(request).execute();
            commonResponse.setCode(response.code());
            String body = response.body().string();
            commonResponse.setData(body);
        } catch (IOException e) {
            e.printStackTrace();
            commonResponse.setCode(ResponseImpl.STATE_UNKNOW_ERROR);
            commonResponse.setData(e.getMessage());
        }
        return commonResponse;
    }

到这里封装就基本完成了,没有其他另类的东西,功能都是很基础的请求
下面有一个简单的使用示例

    使用示例
    IRequest request = new RequestImpl(这里传入url);
    //设置请求头,这里要几个就setHeader几次
    request.setHeader(key,value);
    // 设置请求体 同上
    request.setBody(key,value);
    // 获取一个okhttpclient实例
    IHttpClient mHttpClient = new OkHttpClientImpl();
    // 得到服务器端返回的结果
    IResponse response = mHttpClient.get(request);

注:图片的功能好像不能正常实现,也可能是我app出现问题,下次使用时会着重注意

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 217,542评论 6 504
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 92,822评论 3 394
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 163,912评论 0 354
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,449评论 1 293
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,500评论 6 392
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,370评论 1 302
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,193评论 3 418
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,074评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,505评论 1 314
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,722评论 3 335
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,841评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,569评论 5 345
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,168评论 3 328
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,783评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,918评论 1 269
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,962评论 2 370
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,781评论 2 354

推荐阅读更多精彩内容

  • AFHTTPRequestOperationManager 网络传输协议UDP、TCP、Http、Socket、X...
    Carden阅读 4,337评论 0 12
  • 一、简历准备 1、个人技能 (1)自定义控件、UI设计、常用动画特效 自定义控件 ①为什么要自定义控件? Andr...
    lucas777阅读 5,202评论 2 54
  • 《诗经》又称“诗三百”,是我国最早的诗歌总集。它记录的是从西周初年直至春秋中叶,涵盖地域广泛,黄河以北,直至江汉流...
    车小刀阅读 117评论 0 0
  • 从前慢。一生只够爱一个人。 一大早加班被莫名戳中心动。 换了新的城市,离开生活了8年的B城 来到如今一样快生活的S...
    rabbits先生阅读 330评论 0 2
  • 一、水库人员安排 今天园山街道水库出动管护人员10人次,安保11人次,巡查车辆:摩托车七辆、电动车四辆。重...
    小白_1d34阅读 55评论 0 0