Android教程網
  1. 首頁
  2. Android 技術
  3. Android 手機
  4. Android 系統教程
  5. Android 游戲
 Android教程網 >> Android技術 >> 關於Android編程 >> [Android]Volley源碼分析(五)

[Android]Volley源碼分析(五)

編輯:關於Android編程

請求結果的交付是通過ResponseDelivery接口完成的,它有一個實現類ExecutorDelivery, 主要有postResponse()與postError()兩個方法,分別在請求成功或失敗時將結果提交給請求發起者。   1. 首先,在NetworkDispatcher的run()方法中,當服務器返回響應並解析完後,會調用mDelivery.postResponse(request, response);來提交請求響應。   復制代碼  1  @Override  2     public void run() {  3         Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);  4         Request<?> request;  5         while (true) {  6             try {  7                 // Take a request from the queue.  8                 request = mQueue.take();  9             } catch (InterruptedException e) { 10                 // We may have been interrupted because it was time to quit. 11                 if (mQuit) { 12                     return; 13                 } 14                 continue; 15             } 16  17             try { 18                 request.addMarker("network-queue-take"); 19  20                 // If the request was cancelled already, do not perform the 21                 // network request. 22                 if (request.isCanceled()) { 23                     request.finish("network-discard-cancelled"); 24                     continue; 25                 } 26  27                 addTrafficStatsTag(request); 28  29                 // Perform the network request. 30                 NetworkResponse networkResponse = mNetwork.performRequest(request); 31                 request.addMarker("network-http-complete"); 32  33                 // If the server returned 304 AND we delivered a response already, 34                 // we're done -- don't deliver a second identical response. 35                 if (networkResponse.notModified && request.hasHadResponseDelivered()) { 36                     request.finish("not-modified"); 37                     continue; 38                 } 39  40                 // Parse the response here on the worker thread. 41                 Response<?> response = request.parseNetworkResponse(networkResponse); 42                 request.addMarker("network-parse-complete"); 43  44                 // Write to cache if applicable. 45                 // TODO: Only update cache metadata instead of entire record for 304s. 46                 if (request.shouldCache() && response.cacheEntry != null) { 47                     mCache.put(request.getCacheKey(), response.cacheEntry); 48                     request.addMarker("network-cache-written"); 49                 } 50  51                 // Post the response back. 52                 request.markDelivered(); 53                 mDelivery.postResponse(request, response); 54             } catch (VolleyError volleyError) { 55                 parseAndDeliverNetworkError(request, volleyError); 56             } catch (Exception e) { 57                 VolleyLog.e(e, "Unhandled exception %s", e.toString()); 58                 mDelivery.postError(request, new VolleyError(e)); 59             } 60         } 61     } 復制代碼 2. 看ExecutorDelivery中postResponse()方法的具體實現。其中mResponsePoster是一個Executor。每post一個response,都會調用ResponseDeliveryRunnable的run()方法。在這個run()方法中,會通過mRequest.deliverResponse(mResponse.result)來傳遞response的result,這個result其實就是已經解析好的響應結果,比如一個表示處理結果的字符串或一個User對象。   復制代碼  1 @Override  2     public void postResponse(Request<?> request, Response<?> response) {  3         postResponse(request, response, null);  4     }  5   6     @Override  7     public void postResponse(Request<?> request, Response<?> response, Runnable runnable) {  8         request.markDelivered();  9         request.addMarker("post-response"); 10         mResponsePoster.execute(new ResponseDeliveryRunnable(request, response, runnable)); 11     } 12  13 /** 14      * A Runnable used for delivering network responses to a listener on the 15      * main thread. 16      */ 17     @SuppressWarnings("rawtypes") 18     private class ResponseDeliveryRunnable implements Runnable { 19         private final Request mRequest; 20         private final Response mResponse; 21         private final Runnable mRunnable; 22  23         public ResponseDeliveryRunnable(Request request, Response response, Runnable runnable) { 24             mRequest = request; 25             mResponse = response; 26             mRunnable = runnable; 27         } 28  29         @SuppressWarnings("unchecked") 30         @Override 31         public void run() { 32             // If this request has canceled, finish it and don't deliver. 33             if (mRequest.isCanceled()) { 34                 mRequest.finish("canceled-at-delivery"); 35                 return; 36             } 37  38             // Deliver a normal response or error, depending. 39             if (mResponse.isSuccess()) { 40                 mRequest.deliverResponse(mResponse.result); 41             } else { 42                 mRequest.deliverError(mResponse.error); 43             } 44  45             // If this is an intermediate response, add a marker, otherwise we're done 46             // and the request can be finished. 47             if (mResponse.intermediate) { 48                 mRequest.addMarker("intermediate-response"); 49             } else { 50                 mRequest.finish("done"); 51             } 52  53             // If we have been provided a post-delivery runnable, run it. 54             if (mRunnable != null) { 55                 mRunnable.run(); 56             } 57        } 58     } 復制代碼 3. 既然是通過Request的deliverResponse()來傳遞響應結果,就來看下這個方法, 第二篇中已經知道這個方法是個抽象函數,由它子類來實現。以第一篇中的MyGsonRequest為例,其實現很簡單,就是調用了mListener的onResponse方法。   1 @Override 2     protected void deliverResponse(T response) { 3         mListener.onResponse(response); 4     } 這個mListener就是在主線程實例化MyGsonRequest的時候,傳過來的一個Response.Listener<T>實例,這是MyGsonRequest的構造函數:   復制代碼  1 public MyGsonRequest(int method  2                         , String url                          3                         , Object requestBody  4                         , Class<T> responseClass  5                         , Listener<T> listener  6                         , ErrorListener errorListener) {  7           8         super(method, url, errorListener);  9         this.mRequestBody = requestBody; 10         this.mResponseClass = responseClass; 11         this.mListener = listener; 12         mGson = new Gson(); 13          14     } 復制代碼 這裡mListener也就是第一篇中在主線程中通過createRegisterSuccessListener函數返回的監聽器實例,如下代碼所示。  所以最終會調到這裡的onResponse()方法,來做一些更新UI或提示用戶請求成功之類的操作。請求失敗時,響應錯誤結果的提交與之類似。這樣,Volley就完成了響應結果的交付。   復制代碼  1 private Listener<String> createRegisterSuccessListener() {  2         return new Listener<String>() {  3             @Override  4             public void onResponse(String response) {  5                 if (mProgressDialog != null) {  6                     mProgressDialog.dismiss();  7                 }  8                 Toast.makeText(  9                         RegisterActivity.this, 10                         getString(R.string.msg_register_success), 11                         Toast.LENGTH_SHORT).show(); 12  13             } 14         }; 15     } 復制代碼 這裡還有一個問題, 因為更新UI的操作只能在主線程中進行,那麼ResponseDeliveryRunnable的run()方法不能再新起一個線程來執行,而應該在主線程中執行,這個是如何做到的?   其實還是用的Handler,Looper,MessageQueue的那套機制。 在Volley初始化一個RequestQueue的時候,會調用RequestQueue的如下構造函數,它構建了一個ExecutorDelivery對象,並把一個與主線程的Looper關聯的一個Handler,   1 public RequestQueue(Cache cache, Network network, int threadPoolSize) { 2         this(cache, network, threadPoolSize, 3                 new ExecutorDelivery(new Handler(Looper.getMainLooper()))); 4     } 然後再看下ExecutorDelivery的構造方法, 通過handler的post方法,把ResponseDeliveryRunnable 這個runnable加到了主線程的消息隊列中,所以它的run()方法是在主線程中執行的。   復制代碼 1     public ExecutorDelivery(final Handler handler) { 2         // Make an Executor that just wraps the handler. 3         mResponsePoster = new Executor() { 4             @Override 5             public void execute(Runnable command) { 6                 handler.post(command); 7             } 8         }; 9     }
  1. 上一頁:
  2. 下一頁:
熱門文章
閱讀排行版
Copyright © Android教程網 All Rights Reserved