新項(xiàng)目的一些小思路

新項(xiàng)目開始也有一段時(shí)間了,由于工作以來(lái)幾乎根本??就沒(méi)有大團(tuán)隊(duì)工作經(jīng)驗(yàn),所以關(guān)于架構(gòu)方面的問(wèn)題只能一點(diǎn)點(diǎn)慢慢摸索。雖說(shuō)師傅領(lǐng)進(jìn)門,修行在個(gè)人。但是有沒(méi)有大項(xiàng)目經(jīng)歷,對(duì)工程的架構(gòu)理解還是完全不一樣的。下面是我新項(xiàng)目的一些思路,希望有不對(duì)的地方,還請(qǐng)及時(shí)指出,不吝感激。

工程的目錄結(jié)構(gòu)

項(xiàng)目基于的還是MVC架構(gòu)。至于為什么不用VIP,MVVM嘛,我是不會(huì)說(shuō)用的比較生,不敢在公司趕工的時(shí)候用的。

工程的目錄結(jié)構(gòu)

Mediator

組件化方案。采用的是Case的方案。關(guān)于組件化方案的目的與優(yōu)勢(shì)。

  1. 組件化方案可以使項(xiàng)目解耦。
  2. 可以通過(guò)URL調(diào)用特定頁(yè)面。
  3. 可以使項(xiàng)目架構(gòu)更清晰。

另外還有bang's blog蘑菇街 App 的組件化之路、碼農(nóng)界吳彥祖三篇講述組件化的方法。其實(shí)四個(gè)人將的從本質(zhì)上來(lái)說(shuō)相似。都是利用runtime的反射機(jī)制,轉(zhuǎn)化為實(shí)例對(duì)象,這樣可以根本上解耦。

Mediator組件化

由于APP為公司內(nèi)部審批系統(tǒng)。所以部分頁(yè)面的邏輯會(huì)緊密連接。中間件也就并沒(méi)有像正常Mediator那樣每個(gè)類都創(chuàng)建一個(gè)類別+Target。而是采用分模塊化的形式體現(xiàn)。例如Target_ShowAlert模塊看名字就能知道所有Alert形式的彈出框都依賴這個(gè)中間件。Target_Temporary用來(lái)處理登錄相關(guān)的頁(yè)面。Target_FormFlow則表示一條完整審批流程??赡芤院髸?huì)有其他的審批流程或者模塊那就新建一個(gè)模塊。

Network

采用的是YTKNetwork框架。

曾經(jīng)一度掙扎在 自己封裝&YTKNetwork&RTNetworking

首先是自己封裝:,我認(rèn)為小項(xiàng)目只有很少的網(wǎng)絡(luò)需求的情況下是非常好的。因?yàn)殚_發(fā)速度快上手簡(jiǎn)單。但是面對(duì)較大項(xiàng)目的時(shí)候。就比較吃力了,尤其體現(xiàn)在接口管理和單元測(cè)試上。

YTKNetwork:目前認(rèn)為最為省心的Network封裝庫(kù)了。幾乎能想到的所有需求都能滿足,無(wú)論是緩存、CDN、關(guān)鍵字替換。甚至加載中動(dòng)畫,都非常簡(jiǎn)單。強(qiáng)烈推薦。

RTNetworking:是對(duì)我影響最大的一個(gè)開源庫(kù),具體說(shuō)明請(qǐng)看作者iOS應(yīng)用架構(gòu)談 網(wǎng)絡(luò)層設(shè)計(jì)方案

網(wǎng)絡(luò)結(jié)構(gòu)

YTKNetworking框架采用每個(gè)接口單獨(dú)一個(gè)類的方式來(lái)實(shí)現(xiàn)。這樣的好處是每一個(gè)接口都可以單獨(dú)寫一個(gè)單元測(cè)試,并且可以降低耦合。同時(shí)可以很方便的設(shè)置每個(gè)接口數(shù)據(jù)的轉(zhuǎn)換,每個(gè)接口的緩存控制。非常一目了然,后續(xù)的開發(fā)也非常有條理。

做網(wǎng)絡(luò)請(qǐng)求這一塊遇到了一個(gè)問(wèn)題,就是我們需要對(duì)返回?cái)?shù)據(jù)進(jìn)行統(tǒng)一的業(yè)務(wù)處理,比如說(shuō)我們規(guī)定了state和stateMsg當(dāng)遇到state=0時(shí)需要統(tǒng)一退出登錄并跳轉(zhuǎn)登錄頁(yè)面,這樣的需求目前不知道YTKNetworking如何優(yōu)雅的實(shí)現(xiàn)。目前我的實(shí)現(xiàn)方式有點(diǎn)劍走偏鋒。是利用在接口都為Dictionary的情況下給字典添加一個(gè)統(tǒng)一處理的類別。

業(yè)務(wù)邏輯處理

內(nèi)部實(shí)現(xiàn)的偽碼為:

- (BOOL)isCorrectData {
    if (!self || ![self isKindOfClass:[NSDictionary class]]) {
        return NO;
    }
    //0:業(yè)務(wù)錯(cuò)誤;1:成功;2:登錄錯(cuò)誤;3:系統(tǒng)鏈接錯(cuò)誤
    switch ([self[@"state"] integerValue]) { 
        case ResponseDataStateTypeOperationError: {//業(yè)務(wù)錯(cuò)誤
            if [self stateMessage] [Toast showError:[self stateMessage]];
            return NO;
        } break;
            
        case ResponseDataStateTypeSucceed: {//成功
            return YES;
        } break;
            
        case ResponseDataStateTypeLogInError: {//登錄錯(cuò)誤
            //跳轉(zhuǎn)登錄頁(yè)面
            //showMessage
            return NO;
        } break;
            
        case ResponseDataStateTypeSystemError: {//系統(tǒng)鏈接錯(cuò)誤
            //做一些特殊處理
            return NO;
        } break;
    
        default:
        //一些其他情況
            break;
    }
    return NO;
}

可以看出這樣實(shí)現(xiàn)起來(lái)非常蹩腳。但是又一時(shí)間不知道如何不改變YTKNetworking固有框架的情況下實(shí)現(xiàn)這個(gè)功能。希望有相應(yīng)經(jīng)驗(yàn)的筒子們能指點(diǎn)指點(diǎn)啊。

Model

沒(méi)有太多好說(shuō)的,幾乎所有的Model都是兩個(gè)套路,要么Model只起到數(shù)據(jù)模型的作用,要么則是將部分邏輯從Controller中移植Model,即瘦Model和胖Model。

我目前比較傾向于胖Model,即將一些數(shù)據(jù)轉(zhuǎn)換的活交給Model來(lái)實(shí)現(xiàn),這樣可以使得Controller的清潔。并且由于數(shù)據(jù)展示類型可能會(huì)重復(fù),那么將這個(gè)轉(zhuǎn)化方法提出為擴(kuò)展。則似乎更符合代碼規(guī)范。例如:一個(gè)展示列表中需要提供倒計(jì)時(shí)如4小時(shí)40分前。那么后臺(tái)傳給你的數(shù)據(jù)一定不會(huì)直接是這個(gè)string,而應(yīng)該是一個(gè)時(shí)間戳NSTimeInterval類型這個(gè)類型實(shí)際上是double型數(shù)據(jù),那么此時(shí)你的Model是應(yīng)該提供何種類型的數(shù)據(jù)呢?是定義成

@property(nonatomic, assign) NSTimeInterval timeInterval;

還是

@property(nonatomic, copy) NSString *timeInterval;

亦或者

@property(nonatomic, strong) NSDate *issueTime;

相信大家也有自己的考量了。

View

這個(gè)用到了懶加載+autolayout,實(shí)話說(shuō)在這里用懶加載我還是考慮了很久的,因?yàn)閁I層不像Controller層,這里的控件基本上都是父控件加載的時(shí)候子控件就要?jiǎng)?chuàng)建了,并不存在懶加載的情況。之所以還是用懶加載的方式一方面是為了保持代碼的一致性。另一方面也保證了代碼的易讀性。初始化的代碼放在重寫get方法中實(shí)在是一個(gè)不錯(cuò)的形式。特別對(duì)于有超過(guò)十個(gè)屬性的時(shí)候,幫助特別大。修改的時(shí)候直接奔著目標(biāo)get方法而去。

Controller

因?yàn)閷⒃S多代碼從Controller中分離出去,所以Controller中顯得格外干凈。即使是里面包含tableview 包含篩選,包含下拉刷新上拉加載更多,包含搜索。一樣可以很優(yōu)雅的完成。具體請(qǐng)看TableView DataSource和delegate的分離。

Store

做的是所有和持久化存儲(chǔ)相關(guān)的內(nèi)容

本項(xiàng)目需要做的持久化并不多。其實(shí)就是利用一個(gè)快速讀寫文件類。然后每一個(gè)需要存儲(chǔ)的部分創(chuàng)建一個(gè)類管理一個(gè)文件。進(jìn)行存儲(chǔ)歸結(jié)檔,并暴露出所需要的接口即可。更多需求可以參考YTK的存儲(chǔ)

Libs

放的是一寫第三方庫(kù)。至于為什么不用現(xiàn)在炙手可熱的Cocoapods,Carthage迦太基。主要是因?yàn)楣局贫劝?。月代碼量+注釋覆蓋率+SVN讓我歸回原始。其實(shí)也沒(méi)啥了。就是不能更新有點(diǎn)煩。

工程中使用的Libs

項(xiàng)目中使用的都是比較常見(jiàn)的第三方庫(kù)。感謝開源者們:

CoreLock 手勢(shì)密碼開源庫(kù)源碼。我在其基礎(chǔ)上根據(jù)自己的需求做了相應(yīng)的修改:修改后的版本

GTMBase64 Base64編碼庫(kù)

MBProgressHUD 目前使用率最廣的一款HUD+Message顯示庫(kù)了.

TouchIDManage自己寫的關(guān)于使用TouchID的封裝庫(kù)。非常簡(jiǎn)單

YBDictionary2Model 自己寫的將字典中的屬性轉(zhuǎn)化為property屬性并輸出到控制臺(tái)的庫(kù)

YYKit 目前最炙手可熱的開源庫(kù)之一了吧。使用了其中YYModel、YYText、YYImage 實(shí)在是太棒了。

IQKeyboardManager 一句話實(shí)現(xiàn)鍵盤彈出式動(dòng)態(tài)上移的開源庫(kù)

AFNetworking 目前最著名的objective-c網(wǎng)絡(luò)開源庫(kù)。(ASI由于MRC的原因逐漸的退出了舞臺(tái))

AFDownloadRequestOperation 非常棒的網(wǎng)絡(luò)緩存開源庫(kù),YTKNetworking依賴庫(kù)之一。

YTKNetworking 猿題庫(kù)開源的最出名的網(wǎng)絡(luò)庫(kù)

MJRefresh目前還在更新的下拉刷新庫(kù)

Masonry 偉大的開源庫(kù),算是純代碼autolayout必備庫(kù)了。

SWTableViewCell 左滑出現(xiàn)快速處理模塊的庫(kù),如果要兼容iOS7,這個(gè)庫(kù)就灰常有必要了。

另外還有Notification,所有的通知都要通過(guò)這個(gè)類調(diào)用。這樣就避免了通知寫的太久忘記了有這個(gè)通知的事情了。(掩面而逃)

Toast項(xiàng)目中所有的加載動(dòng)畫。彈出信息都要經(jīng)過(guò)這里包裝。(不要問(wèn)我為什么要脫褲子放屁,等你們突然決定要更換第三方庫(kù)的時(shí)候就知道了)

category

包含了一些項(xiàng)目常用字體,顏色等類別

Common

包含一些通用類。目前只有

Foundation+log.m、正確顯示漢字

LxDBAnything.h、快速打印啊

PrefixHeader.pch、關(guān)于PCH有很多人都在逐漸的拋棄。我也認(rèn)為不應(yīng)該什么類都往PCH中扔。但是完全舍棄對(duì)我來(lái)說(shuō)反而降低了開發(fā)效率。我的PCH中只包含了#import "LxDBAnything.h"

UIDepend.h 引入了一些創(chuàng)建控件是需要的類,不需要將這些類導(dǎo)入到PCH中,那樣會(huì)造成每個(gè)類都引入一次所所有頭文件,造成編譯效率降低。

#ifndef UIDepend_h
#define UIDepend_h

#pragma mark - FontSize


#import "UIColor+OAList.h"
#import "UIFont+OAList.h"

#import "UIView+YBAdd.h"
#import "UILabel+YBAdd.h"
#import "UIButton+YBAdd.h"
#import "UIScreen+YBAdd.h"

#import "Masonry.h"

#import "Toast.h"

#endif /* UIDepend_h */

Supporting Files

放置info.plist、Assets.xcassets、main.m


--by Queuey

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • Android 自定義View的各種姿勢(shì)1 Activity的顯示之ViewRootImpl詳解 Activity...
    passiontim閱讀 179,048評(píng)論 25 709
  • 發(fā)現(xiàn) 關(guān)注 消息 iOS 第三方庫(kù)、插件、知名博客總結(jié) 作者大灰狼的小綿羊哥哥關(guān)注 2017.06.26 09:4...
    肇東周閱讀 15,342評(píng)論 4 61
  • 目錄: 該系列文章預(yù)計(jì)包括: 1 - 簡(jiǎn)介 2 - 連接以及連接過(guò)程解析 3 - 發(fā)送訂閱消息以及發(fā)送過(guò)程 4 -...
    Codepgq閱讀 1,773評(píng)論 7 3
  • 今天春分。微信好友的提示讓我意識(shí)到踏青的季節(jié)到了,可抬眼望去,南京灰蒙蒙的天空,淫雨霏霏,氣溫不到10度,這讓我想...
    天行健志強(qiáng)閱讀 541評(píng)論 1 3
  • 枝頭老鴉無(wú)處還, 東風(fēng)徹夜話凄涼。 千里孤墳裹素妝, 萬(wàn)里河山影傲然。 酌酒默默賞雨寂, 漫天飄飄雪淚寒。 抬頭問(wèn)...
    君惜竹閱讀 1,295評(píng)論 6 6

友情鏈接更多精彩內(nèi)容