日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 运维知识 > Android >内容正文

Android

Android—Retrofit解析

發布時間:2023/12/18 Android 25 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Android—Retrofit解析 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

設計模式:

外觀模式,構建者模式,工廠模式,代理模式,適配器模式,策略模式,觀察者模式

Retrofit網絡通信八步驟

  • 創建Retrofit實例
  • 定義網絡請求接口,并為接口中的方法添加注解
  • 通過動態代理生成網絡請求對象
  • 通過網絡請求適配器將網絡請求對象進行平臺適配
  • 通過網絡請求執行器,發送網絡請求(call)
  • 通過數據解析器解析數據
  • 通過回調執行器,切換線程
  • 用戶在主線程處理返回結果
  • @GET("/user/{user}/repos") Call<ResponseBody> find(@Path("user") String user);//call封裝了整個okhttp的請求Retrofit retrofit = new Retrofit.Builder().baseUrl("https://api.github.com/").addConverterFactory(GsonConverteractory.create())//.addCallAdapterFactory(RxJava2CallAdapterFactory.create()).build();//動態生成代理對象 Request req = retrofit.create(Request.class); //生成一個OKHttpCall的代理對象 Call<ResponseBody> call = req.find(“Mike”); //返回結果 Response<ResponseBody> response = call.execute();

    先看Create方法

    public <T> T create(final Class<T> service) {Utils.validateServiceInterface(service);if (validateEagerly) {eagerlyValidateMethods(service);}//重點看這里return (T) Proxy.newProxyInstance(service.getClassLoader(), new Class<?>[] { service },new InvocationHandler() {private final Platform platform = Platform.get();@Override public Object invoke(Object proxy, Method method, Object[] args)throws Throwable {// If the method is a method from Object then defer to normal invocation.if (method.getDeclaringClass() == Object.class) {return method.invoke(this, args);}if (platform.isDefaultMethod(method)) {return platform.invokeDefaultMethod(method, service, proxy, args);}ServiceMethod<Object, Object> serviceMethod =(ServiceMethod<Object, Object>) loadServiceMethod(method);OkHttpCall<Object> okHttpCall = new OkHttpCall<>(serviceMethod, args);return serviceMethod.callAdapter.adapt(okHttpCall);}}); }

    使用了動態代理,Proxy.newProxyInstance()返回一個代理類對象。

    invoke方法接收三個參數,動態代理對象、我們調用的方法、參數數組;

    loadServiceMethod方法:

    ServiceMethod loadServiceMethod(Method method) {ServiceMethod result;synchronized (serviceMethodCache) {result = serviceMethodCache.get(method);if (result == null) {result = new ServiceMethod.Builder(this, method).build();serviceMethodCache.put(method, result);}}return result; }

    Build類:

    public Builder(Retrofit retrofit, Method method) {this.retrofit = retrofit;this.method = method;// 獲取 method 中的所有注解this.methodAnnotations = method.getAnnotations();// 獲取 method 中方法的參數類型this.parameterTypes = method.getGenericParameterTypes();// 獲得參數的值this.parameterAnnotationsArray = method.getParameterAnnotations(); }

    build()方法主要內容

    // 根據 retrofit 對象的 CallAdapterFactory 為 ServiceMethod 創建一個 callAdapter callAdapter = createCallAdapter(); // 根據 retrofit 對象創建一個 responseConverter,默認是一個 BuildInConveter responseConverter = createResponseConverter(); // 解析 method 的所有注解 for (Annotation annotation : methodAnnotations) {parseMethodAnnotation(annotation); }

    所以ServiceMethod主要封裝了callAdapterresponseConverter ,對注解進行了解析,對后面網絡請求做準備。

    看回Create方法的代碼

    return serviceMethod.callAdapter.adapt(okHttpCall);

    最后是調用了callAdapter的adapt方法,如果我們添加了RxJava2CallAdapter

    @Override public Object adapt(Call<R> call) {Observable<Response<R>> responseObservable = isAsync? new CallEnqueueObservable<>(call): new CallExecuteObservable<>(call);Observable<?> observable;if (isResult) {observable = new ResultObservable<>(responseObservable);} else if (isBody) {observable = new BodyObservable<>(responseObservable);} else {observable = responseObservable;}if (scheduler != null) {observable = observable.subscribeOn(scheduler);}if (isFlowable) {return observable.toFlowable(BackpressureStrategy.LATEST);}if (isSingle) {return observable.singleOrError();}if (isMaybe) {return observable.singleElement();}if (isCompletable) {return observable.ignoreElements();}return observable; }

    所以如果添加了RxJava2CallAdapter就返回observal對象。

    Retrofit中還有一個Converter?,與CallAdapter一樣重要,用戶可以根據需求對這兩個進行自由擴展。

    Okhttp中服務器返回的數據源就是ResponseBody對象。所以我們的目標就是對ResponseBody進行解析:

    T convert(ResponseBody value){//do convert and return t }

    ?Retrofit不僅可以對ResponseBody進行轉換,也可以對RequestBody進行轉換;具體其內部提供了一個Convert.Factory:

    abstract class Factory {//對ResponseBody進行數據轉換的轉換器public @Nullable Converter<ResponseBody, ?> responseBodyConverter(Type type,Annotation[] annotations, Retrofit retrofit) {return null;}//將未知數據轉換成RequestBody的轉換器public @Nullable Converter<?, RequestBody> requestBodyConverter(Type type,Annotation[] parameterAnnotations, Annotation[] methodAnnotations, Retrofit retrofit) {return null;}//將未知數據轉換成String類型的數據轉換器public @Nullable Converter<?, String> stringConverter(Type type, Annotation[] annotations,Retrofit retrofit) {return null;} }

    開頭構建Retrofit對象的

    .addConverterFactory(GsonConverterFactory.create()) //添加Gson

    就是用來添加Gson對象的

    public static GsonConverterFactory create() {return create(new Gson());}public static GsonConverterFactory create(Gson gson) {return new GsonConverterFactory(gson);}class GsonConverterFactory extends Converter.Factory{//持有一個gson對象用來講原始數據轉換成JavaBeanprivate final Gson gson;private GsonConverterFactory(Gson gson) {this.gson = gson;}}

    具體轉換過程可以看Gson原理分析。

    創作挑戰賽新人創作獎勵來咯,堅持創作打卡瓜分現金大獎

    總結

    以上是生活随笔為你收集整理的Android—Retrofit解析的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。