1. 程式人生 > >利用程式碼掃描工具提升Android程式碼健壯性

利用程式碼掃描工具提升Android程式碼健壯性

Android Lint

在保證你的應用功能需求測試通過的同時,保證你的程式碼沒有結構性錯誤也非常的重要。結構糟糕的程式碼,將會對你的應用可靠性和效率帶來不利的影響,也會讓程式碼難以維護。比如,你的xml中有未被使用的名稱空間,既佔用了空間,也會招致多餘的處理。其他的錯誤,例如使用過時的api或者目標版本不支援的api,也會讓程式碼執行不正確。

概述

Android Studio提供了一個叫做Lint的程式碼掃描工具,能夠幫助你輕鬆地找出並修復程式碼中的質量問題,不需要執行應用和寫測試用例。工具把每個問題按照問題描述和嚴重級別報告給你,你也可以配置錯誤的嚴重等級忽略與專案不相關的錯誤,也可以提升錯誤的等級。這個工具有命令列結果,你可以很方便的整合進來做自動測試。
下面是Lint工具的工作原理。

這裡寫圖片描述

Lint掃描流程
Application source files
應用資原始檔包括程式碼,xml檔案,圖示檔案,混淆器配置檔案。

lint.xml檔案
用來配置你想排除或者自定義的問題嚴重等級。

Lint工具
這個就是靜態程式碼掃描的工具。

掃描結果
可以在控制檯或者事件日誌等地方看到掃描結果。

在Android Studio中執行

在Android Studio中,當你編譯程式的時候,Lint會自動執行。檢視修改問題嚴重等級,你可以開啟設定File > Settings > Editor > Inspections 進行修改,這個是windows的設定,mac基本大同小異。在build.gradle中也可以修改配置。

android {
    lintOptions {
       // 設定成true關閉lint的分析程序
       quiet true
       // 設定成true, 當發現問題的時候就會終止gradle build
       abortOnError false
       // 設定成true,只報告錯誤
       ignoreWarnings true
       }
       ...
    }

也可以手動執行掃描,在Analyze > Inspect Code下,然後制定掃描的範圍。

在命令列執行lint

lint [flags] <project
directory>

舉個例子,你可以用下面的命令去掃描myproject工程目錄以及子目錄。錯誤的ID是MissingPrefix,只掃描xml檔案沒有名稱空間字首的錯誤。

lint --check MissingPrefix myproject

其他的命令和引數可以通過下面這個方法檢視:

lint --help

lint輸出示例

下面是Lint掃描Earthquake專案後的結果:

$ lint Earthquake

Scanning Earthquake: ...............................................................................................................................
Scanning Earthquake (Phase 2): .......
AndroidManifest.xml:23: Warning: <uses-sdk> tag appears after <application> tag [ManifestOrder]
  <uses-sdk android:minSdkVersion="7" />
  ^
AndroidManifest.xml:23: Warning: <uses-sdk> tag should specify a target API level (the highest verified version; when running on later versions, compatibility behaviors may be enabled) with android:targetSdkVersion="?" [UsesMinSdkAttributes]
  <uses-sdk android:minSdkVersion="7" />
  ^
res/layout/preferences.xml: Warning: The resource R.layout.preferences appears to be unused [UnusedResources]
res: Warning: Missing density variation folders in res: drawable-xhdpi [IconMissingDensityFolder]
0 errors, 4 warnings

輸入了4個警告,0個錯誤。錯誤的原因和位置都已經展示出來了,所以很方便找到並修復他們。

在程式碼和xml中配置lint

如果要忽略部分檢查可以這樣做:

@SuppressLint("NewApi")
@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.main);
@SuppressLint("ParserError")
public class FeedProvider extends ContentProvider {

xml中是這樣的

namespace xmlns:tools="http://schemas.android.com/tools"
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    tools:ignore="UnusedResources" >

    <TextView
        android:text="@string/auto_update_prompt" />
</LinearLayout>
tools:ignore="NewApi,StringFormatInvalid"

Infer

Infer 是facebook推出的一款靜態程式碼掃描工具,支援Objective-C, Java, 和 C。使用過後覺得還不錯,推薦給大家。
我是通過brew安裝的,命令如下:

brew install infer

執行檢查也非常簡單

infer -- gradle xxxx(最後代表你要檢查的專案名)

掃描的時間看專案大小,如果專案很大會特別的久,需要耐心等待。

掃描結果:
這裡寫圖片描述

這裡寫圖片描述

統計了不同的錯誤型別,還有錯誤程式碼的位置很詳細,可能方便很多快找到問題。主要三種錯誤,可能的空指標,資源沒釋放:例如資料庫或者輸入輸出流沒有釋放,context洩露。

有了這些工具幫助我們,我們專案中crash率和效能都得到了大大的提升,使用者體驗提升了不止一點點。