over 4 years ago

在轉入iOS開發團隊前,有一陣子都在設計相同App的Android版和準備基礎建設。現在的App大都是Internet App,並且在考量UI反應時間、體驗和網路頻寬的消耗,通常也會以某種形式(例如:SQLite或檔案)儲存部分資料在行動裝置上,因此,會頻繁地同步伺服器端和行動裝置端之間資料狀態,再加上行動裝置網路的穩定性不如一般網路可靠(不知4G是否會好一點),需要考慮的事情其實蠻多的,只是後來轉入iOS團隊後(Android版本暫緩),這些設計和想法就暫時放在腦中也沒機會整理下來。

最近,Android版本準備開始復工,趁一些瑣碎的空檔時間,把當初想的結構給整理一下,個人對Model與View分離這件事十分堅持,所以基本的架構概念圖大概就如Figure 1所示,這架構圖很generic,應該適合大多數的Internet App。主要分成幾個色塊,綠色是Model的部分,所有商業邏輯所在,這塊原則上會是platform-independent的設計,所以會以Java SE和Android SDK交集的API完成,也就是說在測試這一塊時,完全不需要Android模擬器,用一般JUnit即可,希望用最少時間達到最大的測試涵蓋率。

對習慣把資料結構直接當成Model的人來說,商業邏輯可能會四散在View或是Controller (這Controller指的是MVC中的Controller)中,但對我來說資料結構只是Model的一部分,也就是圖中Domain Data Model那一塊,以什麼邏輯維持資料結構物件的關係,如何回應Use case或user story所定義的系統訊息,這些處理系統訊息的main controller對我來說,通通都屬於Model,也就是圖中Business Logic Managers,責任是透過Web Service Interfaces和伺服器溝通,然後維持資料結構物件間的關係,最後透過DAO Interfaces將狀態永存(Persistence)在行動裝置上。

Figure 1 - Android App Conceptual Architecture

橘色是platform-dependent的實作,例如用Android的SQLite API來實作DAO,然後以Setter InjectionInterface Injection的方式,將platform-dependent的實作注入,為了做到這點,綠色區塊不能直接依賴platform-dependent的實作,因此Web Service Interfaces和DAO Interfaces兩個區塊只定義介面沒有實作,由橘色區塊中的Web Service ImplementationDAO Implementation分別實作這兩個介面,藉此將依賴關係反轉(Dependency inversion),因此也容易把Web Service Interfaces和DAO Interfaces的mock object給Inject進去,方便測試。

橘色區塊還有一個責任是扮演Android Service的角色,Android可以有Service在背景執行,以接下來要開發的App類型來說,能有在背景執行的Service非常有用。當Activity被喚起,只需bind service就能取得所有最新的狀態。

DAO Implementation是platform-dependent的,所以用橘色標示沒什麼大問題,但Web Service Implementation卻是被標示為紫色,主要是因為以JSON格式傳遞資料的Restful Web Services,是有機會只用以Java SE和Android SDK交集的API,搭配Android上也能使用的JSON Library來完成,也就是Web Service Implementation不一定是platform-dependent的實作,有機會能用JUnit來測試。

淺灰色區塊即View的部分,主要是圖中的Android Activities & UI Flow Controls區塊,這塊測試需要Android模擬器或是使用實機,測試時間也較長,但App好不好用,這塊佔了很大的因素。此外,綠色區塊和橘色區塊的API會以synchronous的方式設計,為了不卡住UI,Android SDK本身有一些Asynchronous的輔助類別(例如AsyncTask),但我覺得還不夠好用,所以Asynchronous Supports & UI Components會根據App的體驗需求客製化一些輔助類別,另外提供一些特殊的UI元件,此外,Android不允許非在UI Thread執行中的程式可以變更畫面,所以Asynchronous Supports & UI Components這區塊還要負責將不同Thread回來的更新通知轉到UI Thread中。這個區塊以藍色標示,主要是因為這些元件應該設計成能跨專案共用的,當成是公司的資產,在開發新專案時就能夠使用才是長久之計。

大原則是這樣沒錯,不過準備開發的App會整合一個第三方的遊戲引擎,到時架構可能會有些許調整,例如在Domain Model或Android Service中多一些Interface與遊戲引擎的部分溝通,盡可能用IoC的方式保護Domain Model。最後,為了不讓不同層級的物件相互汙染,應該會用maven (或gradle)的module機制將不同層級的物件歸屬到不同的module中,再利用dependency的方式限制module之間的可見度。希望Android版在需求相對明確(已有iOS版)的情況下,開發能夠順利些。

← Protected Methods in Objective C About Android App Architecture →