1. 程式人生 > >Android打造一個通用的網路請求引擎HttpUtils

Android打造一個通用的網路請求引擎HttpUtils

打造一個通用的網路請求引擎HttpUtils

  • 為什麼要打造這個引擎
  • Xutils的引擎
  • Okhttp的引擎
  • 使用

為什麼要打造這個引擎

自Android 6.0之後,HttpClient被廢,好多APP是不是出現蛋疼的事,趕緊換掉網路請求框架。相容6.0版本。但是想換網路請求不是一件容易的事。你會發現有多好地方呼叫了此網路請求。想徹底換掉得折騰一番。再者,好多時候。因為網上的網路框架很多。xutils、Okhttp、Retrofit等等。在迭代過程中,發現想換個網路框架使用。是一個很蛋疼的事。所以我們為了解決這一痛點,打造一個通用的引擎。

從網路請求談起

網路請求一般也就是下面幾步

1、選擇請求方式
2、穿入請求地址以及請求引數
3、網路請求成功與否的回撥

第一步:我們寫這樣一個引擎介面IHttpEngine

public interface IHttpEngine {

    /**
     * post請求
     * @param url
     * @param params
     * @param httpCallBack
     */
    void post(String url , Map<String,String> params , HttpCallBack httpCallBack);

    /**
     * get請求
     * @param
url * @param params * @param httpCallBack */
void get(String url , Map<String,String> params , HttpCallBack httpCallBack); }

第二步:我們寫自己的一個請求成功與否的回撥

這裡我們既想要拿到網路請求返回的json串,又想拿到解析後的物件。這個自己考慮,至少我覺得這樣似乎更合理一些

public abstract class HttpCallBack<T> {

    /**
     *
     * @param
resultjson 請求成功返回的json串 * @param result 解析好的物件 * * 直接解析好的可操作物件 返回物件不明確,所以這個地方我們需要使用泛型 */
public abstract void onSuccess(String resultjson , T result); public abstract void onFail(Throwable ex); }

第三步:打造我們自己想要的引擎(Xutils)

public class XUtilsHttpEngine implements IHttpEngine{


    @Override
    public void post(String url, Map<String, String> params, final HttpCallBack httpCallBack) {
        //  封裝url引數
        RequestParams requestParams = new RequestParams(url);

        Iterator<Map.Entry<String, String>> iterator = params.entrySet().iterator();
        while (iterator.hasNext()) {
            Map.Entry<String,String> entry = (Map.Entry) iterator.next();
            requestParams.addParameter(entry.getKey(),entry.getValue());
        }

        x.http().post(requestParams, new Callback.CommonCallback<String>() {
            @Override
            public void onSuccess(String result) {// 主執行緒

                // 獲取泛型的型別
                Type genType = httpCallBack.getClass().getGenericSuperclass();
                Type[] params = ((ParameterizedType) genType).getActualTypeArguments();
                Class typeClass = (Class) params[0];

                httpCallBack.onSuccess(result,GsonUtils.jsonToObject(result,typeClass));
            }

            @Override
            public void onError(Throwable ex, boolean isOnCallback) {
                httpCallBack.onFail(ex);
            }

            @Override
            public void onCancelled(CancelledException cex) {
            }

            @Override
            public void onFinished() {
            }
        });
    }

    @Override
    public void get(String url, Map<String, String> params, HttpCallBack httpCallBack) {

    }
}

第四步:引擎已打造完畢,我們現在想要使用該怎麼辦?

1、可能有些同學會說,直接new XUtilsHttpEngine 物件,調裡面的方法不就可以了嘛。確實這樣是可以使用的。但是你會發現我們想要修改成其他網路框架還是那麼困難。根本就沒有達到我們期望的效果。

2、所以這裡我們建立一個HttpUtils的類,通過new 這個類,來調裡面的方法。之後我們想要切換使用OKhttp。只需要在這個類中的構造方法中。建立OKhttp的引擎即可httpEngine = new OkHttpEngine();。

public class HttpUtils {

    private IHttpEngine httpEngine;

    public static Handler handler = new Handler();

    public HttpUtils() {

        //這裡用來切換引擎
//        httpEngine = new XUtilsHttpEngine();
        httpEngine = new OkHttpEngine();
    }


    /**
     * post請求
     * @param url
     * @param params
     * @param httpCallBack
     */
    public void post(String url , Map<String,String> params , HttpCallBack httpCallBack){
        httpEngine.post(url , params ,httpCallBack);
    }

    /**
     * get請求
     * @param url
     * @param params
     * @param httpCallBack
     */
    public void get(String url , Map<String,String> params , HttpCallBack httpCallBack){
        httpEngine.get(url , params ,httpCallBack);
    }
}

使用

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

    }

    public void login(View view){
        doLogin();
    }

    private void doLogin() {
        HttpUtils httpUtils = new HttpUtils();
        Map<String , String> params = new HashMap<>();
        String url = "http://huyong.viewcreator3d.cn/index.php/Api/Ayhyy/admin_login";
        params.put("admin_name","18601135484");
        params.put("admin_password","888888");
        params.put("sign","ayhyyayhyyayhyy");
        httpUtils.post(url, params, new HttpCallBack<UserInfo>() {
            @Override
            public void onSuccess(String resultjson, UserInfo userinfo) {
                Toast.makeText(MainActivity.this,resultjson+"使用者名稱"+userinfo.info.user_info.admin_name,Toast
                        .LENGTH_SHORT)
                        .show();
            }

            @Override
            public void onFail(Throwable ex) {
                Toast.makeText(MainActivity.this,"請求失敗",Toast.LENGTH_SHORT).show();
            }
        });
    }
}

把okHttp的引擎貼出來。想要使用只需要在HttpUtils這個類中的構造方法修改即可

public class OkHttpEngine implements IHttpEngine{


    @Override
    public void post(String url, Map<String, String> params, final HttpCallBack httpCallBack) {

        FormBody.Builder body = new FormBody.Builder();

        Iterator<Map.Entry<String, String>> iterator = params.entrySet().iterator();
        while (iterator.hasNext()) {
            Map.Entry<String,String> entry = (Map.Entry) iterator.next();
            body.add(entry.getKey(),entry.getValue());
        }
        OkHttpClient client = new OkHttpClient();
        Request request = new Request.Builder()
                .url(url)
                .post(body.build())
                .build();
        client.newCall(request).enqueue(new Callback() {
            @Override
            public void onFailure(Call call, IOException e) {
                httpCallBack.onFail(e);
            }

            @Override
            public void onResponse(Call call, final Response response) throws IOException {

                // 獲取泛型的型別
                Type genType = httpCallBack.getClass().getGenericSuperclass();
                Type[] params = ((ParameterizedType) genType).getActualTypeArguments();
                final Class typeClass = (Class) params[0];

                final String result = response.body().string();

                HttpUtils.handler.post(new Runnable() {
                    @Override
                    public void run() {
                        // 把它弄到主執行緒中
                        httpCallBack.onSuccess(result,GsonUtils.jsonToObject(result,typeClass));
                    }
                });

            }
        });
    }

    @Override
    public void get(String url, Map<String, String> params, HttpCallBack httpCallBack) {

    }
}

總結

這裡我可能只是貼出了POST請求,而get請求以及下載、上傳等等都沒有去貼出來。你是我想說的是學程式設計學習的是別人的思想,如果思想領悟,加上動手才會收貨更多。

附原始碼

原始碼地址