1. 程式人生 > >Android主執行緒裡不允許網路操作

Android主執行緒裡不允許網路操作

Keywords: Android UI執行緒/主執行緒 PENALTY_DEATH_ON_NETWORK

Android API > 9 (Honeycomb及之後)版本里,對UI執行緒/主執行緒裡是不允許聯網操作的,如果有網路操作,會丟擲NetworkOnMainThreadException的異常。

1. Thread Policy裡對網路的限制
StrictMode.AndroidBlockGuardPolicy是BlockGuard.Policy的實現,在其onNetwork()方法裡會根據Policy對網路操作檢測:
        public void onNetwork() {
            if ((mPolicyMask & DETECT_NETWORK) == 0) {
                return;
            }
            if ((mPolicyMask & PENALTY_DEATH_ON_NETWORK) != 0) {
                throw new NetworkOnMainThreadException();
            }

            //...
        }
主執行緒裡的聯網操作時會執行這裡的onNetwork(),如果mPolicyMask裡設定了PENALTY_DEATH_ON_NETWORK,NetworkOnMainThreadException異常就會被丟擲。

而對mPolicyMask的PENALTY_DEATH_ON_NETWORK的掩碼的使能操作,有兩個方法:
StrictMode.ThreadPolicy.Builder().penaltyDeathOnNetwork()
StrictMode.enableDeathOnNetwork()

2. 使能主執行緒裡的網路操作限制
從上面分析知道,主執行緒裡的網路操作限制使能可以通過兩個途徑:
第一個StrictMode.ThreadPolicy.Builder().penaltyDeathOnNetwork(),只在StrictModeTest中被使用,tests編譯時才會用到;
第二個StrictMode.enableDeathOnNetwork(),在ActiovityThread.handleBindApplication()中被使用:
        if (data.appInfo.targetSdkVersion > 9) {
            StrictMode.enableDeathOnNetwork();
        }
在每個宣告在sdk api-9以上的系統中應用,執行時都會被使能,也就是檢測是否主執行緒中是否有聯網操作,如果有聯網操作就丟擲NetworkOnMainThreadException異常。