1. 程式人生 > >app版本更新的四種實現方式

app版本更新的四種實現方式

版本更新大致分為四大類:app負責單版本檢測測與更新(自己實現版本更新),通過蘋果商店的自動更新機制進行自動更新和通過第三方平臺實現版本檢測與更新(如:友盟的版本檢測與更新),app和伺服器聯合實現多版本檢測測與更新(自己實現版本更新)方案。 
通過蘋果商店的自動更新機制進行自動更新是,應用更新時,手機會收到蘋果商店的通知,並啟動應用程式的自動更新下載應用並更新。但是可能出現手機收不到版本更新通知(由手機系統自己實現,並非彈出使用者可見的push提示語)的情況和部分應用更新失敗的情況,若你沒有 Apple ID那麼你也使用不了這類官方更新了。最麻煩的是使用者一般都關閉了應用的自動更新和大批量自動更新時必然有部分失敗,並且失敗了就不會再自動更新成功,大都不希望在外面的移動蜂窩網路下自動更新大量應用,那樣你流量會嗖嗖的莫名向上漲。 
看來是自己的應用自己對自己負責更靠譜。版本更新一般分兩類:強制更新和非強制性更新。當然強制更新是你不更新就不能用了,所以雖然霸道,但是也沒有辦法,通常是業務邏輯的大變更才會出現。非強制更新一般是不更新也能用,但是可能不更新部分功能你用不了或看不到,一般給你提供去蘋果商店更新還是繼續使用的選擇。當然這種強制更新本質是有伺服器來判斷,需要拿當前版本號(伺服器資料庫中儲存的應用版本號)和應用傳送的版本號(儲存在伺服器與應用之間的相關會話中)相比較。當然伺服器中的應用版本號在更新時要保證只能增大不能減少,若伺服器的版本號變更需要向所有應用傳送版本更新push通知。由於蘋果稽核應用的時間不能完全確定,並且蘋果不希望有超過他掌控的版本更新,他做的又太完美,只能忽悠他了,等你收到你的應用上架的郵件時再更新你服務中資料庫對應應用版本號了。 
版本更新有四種實現: 
第一種實現和場景,稱為登入時版本更新(包括強制更新和非強制更新),使用者啟動app登入或自動登入時,傳送請求需要帶本應用的當前版本號,服務返回的結果中包含版本更新資訊,並且一般立刻彈出提示模態對話方塊讓使用者選擇操作,當然強制更新只有去蘋果商店一條路。模態對話方塊在點選後跳到蘋果商店,由於跳轉的過程中,應用被自動切換到後臺,所以若是強制更新,從後臺切換到前臺時,由於以前的模態對話方塊由於點選消失還需要再彈出一個,非強制更新就不需要彈了該幹啥就幹啥去。 
判斷強制,只需要看Version的字串的第1個”.”前的字串就可以,非強更新就看ersion的字串的第1和第2”.”間的字串,第3個”.”後的字串都是不需要更新的子版本號。如:強制更新數字字串.非強制更新數字字串.普通子版本數字字串.普通子版本數字字串。7.3.2就是,7是強制更新版本號,3是非強制更新版本號,2是普通子版本號。原來的版本號比7小就是強制更新,原來的版本號比3小就是非強制更新,原來的版本號比7和3都一樣其它後面的字串比2小都不需要更新。所以想讓你的APP具有強制更新和非強制更新,你的第一個版本就要支援這套機制,不然別人裝了你的第一個最老的APP不更新,那麼理論上都能用那個早期的邏輯,你後期的APP再支援這套更新機制也管不了最早期的版本。經過實際釋出版本發現,蘋果只允許釋出含有2個’.‘或以下的版本號,不支援含有三個’.‘或以上的版本號。

第二種實現和場景,稱為PUSH資訊版本更新,屬於執行時版本更新(通常只包括強制更新)的一種,當用戶在使用時,應用有新版本上架(準確的說是伺服器資料庫中對應應用版本號更新),你的服務推送線上使用者push訊息(強制更新才傳送,非強制更新不發這種強制更新push訊息),當用戶收到這個強制更新push訊息,不彈出PUSH訊息,而是默默的把它記錄到記錄到全域性變數中,當然不能彈出模態提示框,那樣可能中斷使用者正在進行的操作,很不友好,當用戶操作某些核心業務事件(搶單,發單等)時才彈出強制更新。另外可以在從後臺切換到前臺時彈出,注意要考慮到操作了一半,有電話過來,去接電話了,若彈出強制更新你以前做的事情都泡湯了,所以這種情況就看你的選擇了。 
第三種實現和場景,心跳版本檢測,,屬於執行時版本更新(通常只包括強制更新)的一種。若有的應用有心跳,當有版本更新是通過心跳的回調發送給客戶端,客戶端存在全域性變數裡,我們又不知道使用者當前具體再做什麼,所以最好別中斷使用者的當前操作,只有當用戶點選重要業務邏輯(如:接單或發單)才彈出強制更新。 
第四種實現和場景,在應用的設定裡增加版本檢測與更新。這種方案已經在2015年3月20日把它放倒了。我們釋出的app就是因為這被駁回過。蘋果稽核時不能有這樣的功能。只所以拎出來說說是因為有部分以前釋出的應用現在仍舊有這類更新。 
判斷強制,只需要看Version的字串的第1個”.”前的字串就可以,非強更新就看ersion的字串的第1和第2”.”間的字串,第3個”.”後的字串都是不需要更新的子版本號。如:強制更新數字字串.非強制更新數字字串.普通子版本數字字串.普通子版本數字字串。7.3.2.4就是,7是強制更新版本號,3是非強制更新版本號,2是普通子版本號,4普通二級子版本號。原來的版本號比7小就是強制更新,原來的版本號比3小就是非強制更新,原來的版本號比7和3都一樣其它後面的字串比2或4小都不需要更新。所以想讓你的APP具有強制更新和非強制更新,你的第一個版本就要支援這套機制,不然別人裝了你的第一個最老的APP不更新,那麼理論上都能用那個早期的邏輯,你後期的APP再支援這套更新機制也管不了最早期的版本。

手機自動更新關閉,開啟就不用再說了吧: 
在設定中,左邊目錄往下啦,看到一個itunes store和app store,選擇點選; 
點選之後看到自動下載的專案:一、應用程式;二、更新;就是後臺聯網有更新的情況下自動下載應用程式和更新軟體。 
我們只要把開關關閉,如果需要更新進入app store選擇手動更新即可,這樣就不會無緣無故耗費流量了。特別是iphone,有時無意識的開著3g或4g網路(有些區域沒有高階基站,訊號弱時會自動切換到2g網路),騷包的人從來沒有關過蜂窩通訊,我是小市民,一般關閉蜂窩通訊,需要時再開啟。注意蘋果由於是個萌萌達,伺服器不在大陸,經常批量自動更新有部分應用自動更新失敗(我統計統計過,一次自動更新10個應用,通常至少2個應用是失敗的), 並且若它失敗了,以後永遠不會再自動成功了,除非再有更新的版本或你把自動更新關閉再開啟,它才給你重新把所有需要更新的應用自動更新一遍。 
這裡寫圖片描述

登入時版本更新的部分程式碼如下:

<code class="hljs objectivec has-numbering" style="display: block; padding: 0px; color: inherit; box-sizing: border-box; font-family: 'Source Code Pro', monospace;font-size:undefined; white-space: pre; border-radius: 0px; word-wrap: normal; background: transparent;">AppDelegate<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.mm</span>檔案
- (<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">void</span>)applicationDidBecomeActive:(<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">UIApplication</span> *)application
{
    <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//    [HomeViewController checkNetWork];</span>
    FLDDLogDebug(@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"g_versionState :%d, g_bVersionUpdatePrompt : %d"</span>, [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_versionState</span>, [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_bVersionUpdatePrompt</span>);

    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span>((NotReachable == [SelfUser currentSelfUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.networkStatus</span>) && (g_showNoNetNotice))
    {
        FLDDLogDebug(@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"applicationDidBecomeActive : g_showNoNetNotice"</span>);
        [HomeViewController checkNetWork];
    }

    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span>((VERSION_STATE_FORCE_UPDATE == [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_versionState</span>) && (!([User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_bVersionUpdatePrompt</span>)) && ([User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_newVersionURL</span> != <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>))
    {
        UIAlertView *alert=[[UIAlertView alloc]initWithTitle:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"版本更新"</span> message:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"檢測到最新版本,請及時更新"</span> delegate:<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">self</span> cancelButtonTitle:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"更新"</span> otherButtonTitles:<span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>];
        alert<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.tag</span> = <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">100</span>;
        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">@try</span>
        {
            [alert show];
            [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_bVersionUpdatePrompt</span> = <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">YES</span>;
        }
        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">@catch</span> (<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSException</span> *exception) {
        }

    }

}


- (<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">BOOL</span>)application:(<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">UIApplication</span> *)application didFinishLaunchingWithOptions:(<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSDictionary</span> *)launchOptions {
        [[<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSNotificationCenter</span> defaultCenter] addObserver:<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">self</span> selector:<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">@selector</span>(updateVersionNotification:) name:UPDATE_VERSION_NOTIFICATION object:<span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>];
.
.
.
}

- (<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">void</span>)updateVersionNotification:(<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSNotification</span> *)notification
{
    [AppDelegate registerForRemoteNotification];

    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span>((VERSION_STATE_FORCE_UPDATE == [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_versionState</span>) && ([User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_newVersionURL</span> != <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>))
    {
        UIAlertView *alert=[[UIAlertView alloc]initWithTitle:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"版本更新"</span> message:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"檢測到最新版本,請及時更新"</span> delegate:<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">self</span> cancelButtonTitle:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"更新"</span> otherButtonTitles:<span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>,<span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>];
        alert<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.tag</span> = <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">100</span>;
        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">@try</span>
        {
            [alert show];
            [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_bVersionUpdatePrompt</span> = <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">YES</span>;
        }
        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">@catch</span> (<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSException</span> *exception) {
        }
    }
    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">else</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span>((VERSION_STATE_REMIND_UPDATE == [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_versionState</span>) && ([User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_newVersionURL</span> != <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>))
    {
        UIAlertView *alert=[[UIAlertView alloc]initWithTitle:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"版本更新"</span> message:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"檢測到最新版本,請及時更新"</span> delegate:<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">self</span> cancelButtonTitle:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"放棄"</span> otherButtonTitles:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"更新"</span>,<span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>];
        alert<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.tag</span> = <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">101</span>;
        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">@try</span>
        {
            [alert show];
        }
        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">@catch</span> (<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSException</span> *exception) {
        }
    }
}


-(<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">void</span>)alertView:(UIAlertView *)alertView clickedButtonAtIndex:(<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSInteger</span>)buttonIndex
{
    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span>([alertView tag] == <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">100</span>)
    {
        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">switch</span> (buttonIndex) {
            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">case</span> <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">0</span>: <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//YES應該做的事</span>
            {
                [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_bVersionUpdatePrompt</span> = <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">NO</span>;
                [[<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">UIApplication</span> sharedApplication] openURL:[<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSURL</span> URLWithString:[User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_newVersionURL</span>]];
                <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">break</span>;
            }
        }
    }
    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">else</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span>([alertView tag] == <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">101</span>)
    {
        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">switch</span> (buttonIndex) {
            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">case</span> <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">0</span>:<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//NO應該做的事</span>
            {
                <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//[User currentUser].g_bVersionUpdatePrompt = NO;</span>
                [[<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSNotificationCenter</span> defaultCenter] postNotificationName:LOGIN_NOTIFICATION object:<span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>];
                <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">break</span>;
            }
            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">case</span> <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">1</span>: <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//YES應該做的事</span>
            {
                <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//[User currentUser].g_bVersionUpdatePrompt = NO;</span>
                [[<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">UIApplication</span> sharedApplication] openURL:[<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSURL</span> URLWithString:[User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_newVersionURL</span>]];
                <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">break</span>;
            }

        }
    }
}

HomeViewController<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.m</span>檔案
- (<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">void</span>)autoLogin
{
    .
    .
    .
    [[<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSNotificationCenter</span> defaultCenter] postNotificationName:UPDATE_VERSION_NOTIFICATION object:<span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>];
    .
    .
    .
}

- (<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">void</span>)alertView:(UIAlertView *)alertView clickedButtonAtIndex:(<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSInteger</span>)buttonIndex
{
    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (alertView<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.tag</span> == <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">1010</span>)
    {
        _isAlertCherkNet = <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">NO</span>;

        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (_needSendNotice)
        {
            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">self</span><span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.isHaveNet</span>)
            {
                _needSendNotice = <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">NO</span>;
                _isAlertCherkNet = <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">NO</span>;
                [[<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSNotificationCenter</span> defaultCenter] postNotificationName:UPDATE_VERSION_NOTIFICATION object:<span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>];
            }
            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">else</span>
            {
                <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span>(!_isAlertCherkNet && !_isAlertSrvFail)
                {
                    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">self</span><span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.alertView</span> = [[UIAlertView alloc] initWithTitle:<span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span> message:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"當前無網路,請開啟網路"</span> delegate:<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">self</span> cancelButtonTitle:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"確定"</span> otherButtonTitles:<span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>, <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>];
                    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">self</span><span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.alertView</span><span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.tag</span> = <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">1010</span>;
                    _isAlertCherkNet = <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">YES</span>;
                    [<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">self</span><span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.alertView</span>  show];
                    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">self</span><span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.alertView</span> = <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>;
                }
            }

        }
    }
}
LoginViewController<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.m</span>檔案
-(<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">void</span>)btn{
    .
    .
    .
    [[<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSNotificationCenter</span> defaultCenter] postNotificationName:UPDATE_VERSION_NOTIFICATION object:<span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>];
    .
    .
    .
}


User<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.m</span>檔案
+ (<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">void</span>)loginWithParams:(<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSDictionary</span> *)params block:(<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">void</span> (^)(<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSArray</span> *, <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSError</span> *))block
{
    <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSMutableDictionary</span> *muParams = [<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSMutableDictionary</span> dictionaryWithDictionary:params];

    <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSString</span> *version = [AppManager getVersion];
    <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSString</span> *model = [AppManager getDeviceModel];
    <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSString</span> *iOSVersion = [AppManager getIOSVersion];

    [muParams setObject:version forKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"version"</span>];
    [muParams setObject:model forKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"phoneType"</span>];
    [muParams setObject:iOSVersion forKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"phoneSystem"</span>];
    [muParams setObject:g_loginCmd forKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"cmdCode"</span>];

    [[API shareAPI] GET:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"loginWithFixedPasswordJsonPhone.htm"</span> params:muParams success:^(AFHTTPRequestOperation *operation, <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">id</span> responseObject) {

<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//        [[NSNotificationCenter defaultCenter] postNotificationName:REMOVE_LOCALNOTIFICATION_NOTIFICATION object:nil];//登入成功後,取消之前所有不是本使用者的催單提醒</span>

        <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSString</span> *cookie = [operation<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.response</span><span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.allHeaderFields</span> objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"Set-Cookie"</span>];<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//儲存Cookie(僅登入成功後儲存)</span>
        [AppManager setUserDefaultsValue:cookie key:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"cookie"</span>];

        <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSDictionary</span> *responseBody = [responseObject objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"body"</span>];
        .
        .
        .
        [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.grabMessage</span> = [[responseBody objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"grabCityNotEqual"</span>] toString];

        [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_newVersionURL</span> = <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>;
        <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSString</span> *hasNewVersion= [[responseBody objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"hasNewVersion"</span>] toString];
        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span>([hasNewVersion isEqualToString:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"0"</span>])
        {
            [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_versionState</span> = VERSION_STATE_NO_UPDATE;
        }
        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">else</span>
        {
            <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSString</span> *needUpgrade= [[responseBody objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"needUpgrade"</span>] toString];
            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span>([needUpgrade isEqualToString:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"1"</span>])
            {
                [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_versionState</span> = VERSION_STATE_FORCE_UPDATE;
            }
            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">else</span>
            {
                [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_versionState</span> = VERSION_STATE_REMIND_UPDATE;
            }
            <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSString</span> *downloadUrl= [[responseBody objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"downloadUrl"</span>] toString];
            [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_newVersionURL</span> = downloadUrl;
        }

        <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSArray</span> *districts = [[responseBody objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"countyList"</span>] objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"rows"</span>];


        <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSMutableArray</span> *muArray = [<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSMutableArray</span> array];

        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">for</span> (<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSDictionary</span> *attribute in districts) {
            District *district = [[District alloc] initWithAttributes:attribute];
            [muArray addObject:district];
        }

        [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.districts</span> = [<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSArray</span> arrayWithArray:muArray];

        [[User currentUser] saveUserInfo];
<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//        [AppManager addUserRemindNotification];</span>
<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//        [AppManager addCurrentOrderRemind];</span>


        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (block) {
            block([<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSArray</span> arrayWithArray:muArray], <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>);
        }

    } failure:^(AFHTTPRequestOperation *operation, <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSError</span> *error) {

        [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.state</span> = @<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"-1"</span>;

        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (block) {
            block(@[], error);
        }
    }];

}

+ (<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">void</span>)reLoginWithParams:(<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSDictionary</span> *)params block:(<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">void</span> (^)(<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSArray</span> *, <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSError</span> *))block
{
    <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSMutableDictionary</span> *muParams = [<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSMutableDictionary</span> dictionaryWithDictionary:params];

    <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSString</span> *version = [AppManager getVersion];
    <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSString</span> *model = [AppManager getDeviceModel];
    <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSString</span> *iOSVersion = [AppManager getIOSVersion];

    [muParams setObject:version forKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"version"</span>];
    [muParams setObject:model forKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"phoneType"</span>];
    [muParams setObject:iOSVersion forKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"phoneSystem"</span>];
    [muParams setObject:g_reloginCmd forKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"cmdCode"</span>];
    [AppManager setUserDefaultsValue:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">""</span> key:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"cookie"</span>];

    [[API shareAPI] GET:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"reLoginWithFixedPasswordJsonPhone.htm"</span> params:muParams success:^(AFHTTPRequestOperation *operation, <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">id</span> responseObject) {

<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//        [[NSNotificationCenter defaultCenter] postNotificationName:REMOVE_LOCALNOTIFICATION_NOTIFICATION object:nil];//登入成功後,取消之前所有不是本使用者的催單提醒</span>

        <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSString</span> *cookie = [operation<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.response</span><span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.allHeaderFields</span> objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"Set-Cookie"</span>];<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//儲存Cookie(僅登入成功後儲存)</span>

        FLDDLogDebug(@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"login cookie\n ----------\n%@\n------------\n"</span>, cookie);
        [AppManager setUserDefaultsValue:cookie key:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"cookie"</span>];

        <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSDictionary</span> *responseBody = [responseObject objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"body"</span>];
        .
        .
        .
        [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_newVersionURL</span> = <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>;
        <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSString</span> *hasNewVersion= [[responseBody objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"hasNewVersion"</span>] toString];
        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span>([hasNewVersion isEqualToString:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"0"</span>])
        {
            [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_versionState</span> = VERSION_STATE_NO_UPDATE;
        }
        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">else</span>
        {
            <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSString</span> *needUpgrade= [[responseBody objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"needUpgrade"</span>] toString];
            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span>([needUpgrade isEqualToString:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"1"</span>])
            {
                [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_versionState</span> = VERSION_STATE_FORCE_UPDATE;
            }
            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">else</span>
            {
                [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_versionState</span> = VERSION_STATE_REMIND_UPDATE;
            }
            <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSString</span> *downloadUrl= [[responseBody objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"downloadUrl"</span>] toString];
            [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.g_newVersionURL</span> = downloadUrl;
        }

        <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSArray</span> *districts = [[responseBody objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"countyList"</span>] objectForKey:@<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"rows"</span>];


        <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSMutableArray</span> *muArray = [<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSMutableArray</span> array];

        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">for</span> (<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSDictionary</span> *attribute in districts) {
            District *district = [[District alloc] initWithAttributes:attribute];
            [muArray addObject:district];
        }

        [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.districts</span> = [<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSArray</span> arrayWithArray:muArray];

        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">for</span> (<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSDictionary</span> *attribute in districts) {
            District *district = [[District alloc] initWithAttributes:attribute];
            [muArray addObject:district];
        }

        [[User currentUser] saveUserInfo];
<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//        [AppManager addUserRemindNotification];</span>
<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//        [AppManager addCurrentOrderRemind];</span>

        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (block) {
            block([<span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSArray</span> arrayWithArray:muArray], <span class="hljs-literal" style="color: rgb(0, 102, 102); box-sizing: border-box;">nil</span>);

        }

    } failure:^(AFHTTPRequestOperation *operation, <span class="hljs-built_in" style="color: rgb(102, 0, 102); box-sizing: border-box;">NSError</span> *error) {

        [User currentUser]<span class="hljs-variable" style="color: rgb(102, 0, 102); box-sizing: border-box;">.state</span> = @<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"-1"</span>;

        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (block) {
            block(@[], error);
        }
    }];
}</code><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right-width: 1px; border-right-style: solid; border-right-color: rgb(221, 221, 221); list-style: none; text-align: right; background-color: rgb(238, 238, 238);"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li><li style="box-sizing: border-box; padding: 0px 5px;">6</li><li style="box-sizing: border-box; padding: 0px 5px;">7</li><li style="box-sizing: border-box; padding: 0px 5px;">8</li><li style="box-sizing: border-box; padding: 0px 5px;">9</li><li style="box-sizing: border-box; padding: 0px 5px;">10</li><li style="box-sizing: border-box; padding: 0px 5px;">11</li><li style="box-sizing: border-box; padding: 0px 5px;">12</li><li style="box-sizing: border-box; padding: 0px 5px;">13</li><li style="box-sizing: border-box; padding: 0px 5px;">14</li><li style="box-sizing: border-box; padding: 0px 5px;">15</li><li style="box-sizing: border-box; padding: 0px 5px;">16</li><li style="box-sizing: border-box; padding: 0px 5px;">17</li><li style="box-sizing: border-box; padding: 0px 5px;">18</li><li style="box-sizing: border-box; padding: 0px 5px;">19</li><li style="box-sizing: border-box; padding: 0px 5px;">20</li><li style="box-sizing: border-box; padding: 0px 5px;">21</li><li style="box-sizing: border-box; padding: 0px 5px;">22</li><li style="box-sizing: border-box; padding: 0px 5px;">23</li><li style="box-sizing: border-box; padding: 0px 5px;">24</li><li style="box-sizing: border-box; padding: 0px 5px;">25</li><li style="box-sizing: border-box; padding: 0px 5px;">26</li><li style="box-sizing: border-box; padding: 0px 5px;">27</li><li style="box-sizing: border-box; padding: 0px 5px;">28</li><li style="box-sizing: border-box; padding: 0px 5px;">29</li><li style="box-sizing: border-box; padding: 0px 5px;">30</li><li style="box-sizing: border-box; padding: 0px 5px;">31</li><li style="box-sizing: border-box; padding: 0px 5px;">32</li><li style="box-sizing: border-box; padding: 0px 5px;">33</li><li style="box-sizing: border-box; padding: 0px 5px;">34</li><li style="box-sizing: border-box; padding: 0px 5px;">35</li><li style="box-sizing: border-box; padding: 0px 5px;">36</li><li style="box-sizing: border-box; padding: 0px 5px;">37</li><li style="box-sizing: border-box; padding: 0px 5px;">38</li><li style="box-sizing: border-box; padding: 0px 5px;">39</li><li style="box-sizing: border-box; padding: 0px 5px;">40</li><li style="box-sizing: border-box; padding: 0px 5px;">41</li><li style="box-sizing: border-box; padding: 0px 5px;">42</li><li style="box-sizing: border-box; padding: 0px 5px;">43</li><li style="box-sizing: border-box; padding: 0px 5px;">44</li><li style="box-sizing: border-box; padding: 0px 5px;">45</li><li style="box-sizing: border-box; padding: 0px 5px;">46</li><li style="box-sizing: border-box; padding: 0px 5px;">47</li><li style="box-sizing: border-box; padding: 0px 5px;">48</li><li style="box-sizing: border-box; padding: 0px 5px;">49</li><li style="box-sizing: border-box; padding: 0px 5px;">50</li><li style="box-sizing: border-box; padding: 0px 5px;">51</li><li style="box-sizing: border-box; padding: 0px 5px;">52</li><li style="box-sizing: border-box; padding: 0px 5px;">53</li><li style="box-sizing: border-box; padding: 0px 5px;">54</li><li style="box-sizing: border-box; padding: 0px 5px;">55</li><li style="box-sizing: border-box; padding: 0px 5px;">56</li><li style="box-sizing: border-box; padding: 0px 5px;">57</li><li style="box-sizing: border-box; padding: 0px 5px;">58</li><li style="box-sizing: border-box; padding: 0px 5px;">59</li><li style="box-sizing: border-box; padding: 0px 5px;">60</li><li style="box-sizing: border-box; padding: 0px 5px;">61</li><li style="box-sizing: border-box; padding: 0px 5px;">62</li><li style="box-sizing: border-box; padding: 0px 5px;">63</li><li style="box-sizing: border-box; padding: 0px 5px;">64</li><li style="box-sizing: border-box; padding: 0px 5px;">65</li><li style="box-sizing: border-box; padding: 0px 5px;">66</li><li style="box-sizing: border-box; padding: 0px 5px;">67</li><li style="box-sizing: border-box; padding: 0px 5px;">68</li><li style="box-sizing: border-box; padding: 0px 5px;">69</li><li style="box-sizing: border-box; padding: 0px 5px;">70</li><li style="box-sizing: border-box; padding: 0px 5px;">71</li><li style="box-sizing: border-box; padding: 0px 5px;">72</li><li style="box-sizing: border-box; padding: 0px 5px;">73</li><li style="box-sizing: border-box; padding: 0px 5px;">74</li><li style="box-sizing: border-box; padding: 0px 5px;">75</li><li style="box-sizing: border-box; padding: 0px 5px;">76</li><li style="box-sizing: border-box; padding: 0px 5px;">77</li><li style="box-sizing: border-box; padding: 0px 5px;">78</li><li style="box-sizing: border-box; padding: 0px 5px;">79</li><li style="box-sizing: border-box; padding: 0px 5px;">80</li><li style="box-sizing: border-box; padding: 0px 5px;">81</li><li style="box-sizing: border-box; padding: 0px 5px;">82</li><li style="box-sizing: border-box; padding: 0px 5px;">83</li><li style="box-sizing: border-box; padding: 0px 5px;">84</li><li style="box-sizing: border-box; padding: 0px 5px;">85</li><li style="box-sizing: border-box; padding: 0px 5px;">86</li><li style="box-sizing: border-box; padding: 0px 5px;">87</li><li style="box-sizing: border-box; padding: 0px 5px;">88</li><li style="box-sizing: border-box; padding: 0px 5px;">89</li><li style="box-sizing: border-box; padding: 0px 5px;">90</li><li style="box-sizing: border-box; padding: 0px 5px;">91</li><li style="box-sizing: border-box; padding: 0px 5px;">92</li><li style="box-sizing: border-box; padding: 0px 5px;">93</li><li style="box-sizing: border-box; padding: 0px 5px;">94</li><li style="box-sizing: border-box; padding: 0px 5px;">95</li><li style="box-sizing: border-box; padding: 0px 5px;">96</li><li style="box-sizing: border-box; padding: 0px 5px;">97</li><li style="box-sizing: border-box; padding: 0px 5px;">98</li><li style="box-sizing: border-box; padding: 0px 5px;">99</li><li style="box-sizing: border-box; padding: 0px 5px;">100</li><li style="box-sizing: border-box; padding: 0px 5px;">101</li><li style="box-sizing: border-box; padding: 0px 5px;">102</li><li style="box-sizing: border-box; padding: 0px 5px;">103</li><li style="box-sizing: border-box; padding: 0px 5px;">104</li><li style="box-sizing: border-box; padding: 0px 5px;">105</li><li style="box-sizing: border-box; padding: 0px 5px;">106</li><li style="box-sizing: border-box; padding: 0px 5px;">107</li><li style="box-sizing: border-box; padding: 0px 5px;">108</li><li style="box-sizing: border-box; padding: 0px 5px;">109</li><li style="box-sizing: border-box; padding: 0px 5px;">110</li><li style="box-sizing: border-box; padding: 0px 5px;">111</li><li style="box-sizing: border-box; padding: 0px 5px;">112</li><li style="box-sizing: border-box; padding: 0px 5px;">113</li><li style="box-sizing: border-box; padding: 0px 5px;">114</li><li style="box-sizing: border-box; padding: 0px 5px;">115</li><li style="box-sizing: border-box; padding: 0px 5px;">116</li><li style="box-sizing: border-box; padding: 0px 5px;">117</li><li style="box-sizing: border-box; padding: 0px 5px;">118</li><li style="box-sizing: border-box; padding: 0px 5px;">119</li><li style="box-sizing: border-box; padding: 0px 5px;">120</li><li style="box-sizing: border-box; padding: 0px 5px;">121</li><li style="box-sizing: border-box; padding: 0px 5px;">122</li><li style="box-sizing: border-box; padding: 0px 5px;">123</li><li style="box-sizing: border-box; padding: 0px 5px;">124</li><li style="box-sizing: border-box; padding: 0px 5px;">125</li><li style="box-sizing: border-box; padding: 0px 5px;">126</li><li style="box-sizing: border-box; padding: 0px 5px;">127</li><li style="box-sizing: border-box; padding: 0px 5px;">128</li><li style="box-sizing: border-box; padding: 0px 5px;">129</li><li style="box-sizing: border-box; padding: 0px 5px;">130</li><li style="box-sizing: border-box; padding: 0px 5px;">131</li><li style="box-sizing: border-box; padding: 0px 5px;">132</li><li style="box-sizing: border-box; padding: 0px 5px;">133</li><li style="box-sizing: border-box; padding: 0px 5px;">134</li><li style="box-sizing: border-box; padding: 0px 5px;">135</li><li style="box-sizing: border-box; padding: 0px 5px;">136</li><li style="box-sizing: border-box; padding: 0px 5px;">137</li><li style="box-sizing: border-box; padding: 0px 5px;">138</li><li style="box-sizing: border-box; padding: 0px 5px;">139</li><li style="box-sizing: border-box; padding: 0px 5px;">140</li><li style="box-sizing: border-box; padding: 0px 5px;">141</li><li style="box-sizing: border-box; padding: 0px 5px;">142</li><li style="box-sizing: border-box; padding: 0px 5px;">143</li><li style="box-sizing: border-box; padding: 0px 5px;">144</li><li style="box-sizing: border-box; padding: 0px 5px;">145</li><li style="box-sizing: border-box; padding: 0px 5px;">146</li><li style="box-sizing: border-box; padding: 0px 5px;">147</li><li style="box-sizing: border-box; padding: 0px 5px;">148</li><li style="box-sizing: border-box; padding: 0px 5px;">149</li><li style="box-sizing: border-box; padding: 0px 5px;">150</li><li style="box-sizing: border-box; padding: 0px 5px;">151</li><li style="box-sizing: border-box; padding: 0px 5px;">152</li><li style="box-sizing: border-box; padding: 0px 5px;">153</li><li style="box-sizing: border-box; padding: 0px 5px;">154</li><li style="box-sizing: border-box; padding: 0px 5px;">155</li><li style="box-sizing: border-box; padding: 0px 5px;">156</li><li style="box-sizing: border-box; padding: 0px 5px;">157</li><li style="box-sizing: border-box; padding: 0px 5px;">158</li><li style="box-sizing: border-box; padding: 0px 5px;">159</li><li style="box-sizing: border-box; padding: 0px 5px;">160</li><li style="box-sizing: border-box; padding: 0px 5px;">161</li><li style="box-sizing: border-box; padding: 0px 5px;">162</li><li style="box-sizing: border-box; padding: 0px 5px;">163</li><li style="box-sizing: border-box; padding: 0px 5px;">164</li><li style="box-sizing: border-box; padding: 0px 5px;">165</li><li style="box-sizing: border-box; padding: 0px 5px;">166</li><li style="box-sizing: border-box; padding: 0px 5px;">167</li><li style="box-sizing: border-box; padding: 0px 5px;">168</li><li style="box-sizing: border-box; padding: 0px 5px;">169</li><li style="box-sizing: border-box; padding: 0px 5px;">170</li><li style="box-sizing: border-box; padding: 0px 5px;">171</li><li style="box-sizing: border-box; padding: 0px 5px;">172</li><li style="box-sizing: border-box; padding: 0px 5px;">173</li><li style="box-sizing: border-box; padding: 0px 5px;">174</li><li style="box-sizing: border-box; padding: 0px 5px;">175</li><li style="box-sizing: border-box; padding: 0px 5px;">176</li><li style="box-sizing: border-box; padding: 0px 5px;">177</li><li style="box-sizing: border-box; padding: 0px 5px;">178</li><li style="box-sizing: border-box; padding: 0px 5px;">179</li><li style="box-sizing: border-box; padding: 0px 5px;">180</li><li style="box-sizing: border-box; padding: 0px 5px;">181</li><li style="box-sizing: border-box; padding: 0px 5px;">182</li><li style="box-sizing: border-box; padding: 0px 5px;">183</li><li style="box-sizing: border-box; padding: 0px 5px;">184</li><li style="box-sizing: border-box; padding: 0px 5px;">185</li><li style="box-sizing: border-box; padding: 0px 5px;">186</li><li style="box-sizing: border-box; padding: 0px 5px;">187</li><li style="box-sizing: border-box; padding: 0px 5px;">188</li><li style="box-sizing: border-box; padding: 0px 5px;">189</li><li style="box-sizing: border-box; padding: 0px 5px;">190</li><li style="box-sizing: border-box; padding: 0px 5px;">191</li><li style="box-sizing: border-box; padding: 0px 5px;">192</li><li style="box-sizing: border-box; padding: 0px 5px;">193</li><li style="box-sizing: border-box; padding: 0px 5px;">194</li><li style="box-sizing: border-box; padding: 0px 5px;">195</li><li style="box-sizing: border-box; padding: 0px 5px;">196</li><li style="box-sizing: border-box; padding: 0px 5px;">197</li><li style="box-sizing: border-box; padding: 0px 5px;">198</li><li style="box-sizing: border-box; padding: 0px 5px;">199</li><li style="box-sizing: border-box; padding: 0px 5px;">200</li><li style="box-sizing: border-box; padding: 0px 5px;">201</li><li style="box-sizing: border-box; padding: 0px 5px;">202</li><li style="box-sizing: border-box; padding: 0px 5px;">203</li><li style="box-sizing: border-box; padding: 0px 5px;">204</li><li style="box-sizing: border-box; padding: 0px 5px;">205</li><li style="box-sizing: border-box; padding: 0px 5px;">206</li><li style="box-sizing: border-box; padding: 0px 5px;">207</li><li style="box-sizing: border-box; padding: 0px 5px;">208</li><li style="box-sizing: border-box; padding: 0px 5px;">209</li><li style="box-sizing: border-box; padding: 0px 5px;">210</li><li style="box-sizing: border-box; padding: 0px 5px;">211</li><li style="box-sizing: border-box; padding: 0px 5px;">212</li><li style="box-sizing: border-box; padding: 0px 5px;">213</li><li style="box-sizing: border-box; padding: 0px 5px;">214</li><li style="box-sizing: border-box; padding: 0px 5px;">215</li><li style="box-sizing: border-box; padding: 0px 5px;">216</li><li style="box-sizing: border-box; padding: 0px 5px;">217</li><li style="box-sizing: border-box; padding: 0px 5px;">218</li><li style="box-sizing: border-box; padding: 0px 5px;">219</li><li style="box-sizing: border-box; padding: 0px 5px;">220</li><li style="box-sizing: border-box; padding: 0px 5px;">221</li><li style="box-sizing: border-box; padding: 0px 5px;">222</li><li style="box-sizing: border-box; padding: 0px 5px;">223</li><li style="box-sizing: border-box; padding: 0px 5px;">224</li><li style="box-sizing: border-box; padding: 0px 5px;">225</li><li style="box-sizing: border-box; padding: 0px 5px;">226</li><li style="box-sizing: border-box; padding: 0px 5px;">227</li><li style="box-sizing: border-box; padding: 0px 5px;">228</li><li style="box-sizing: border-box; padding: 0px 5px;">229</li><li style="box-sizing: border-box; padding: 0px 5px;">230</li><li style="box-sizing: border-box; padding: 0px 5px;">231</li><li style="box-sizing: border-box; padding: 0px 5px;">232</li><li style="box-sizing: border-box; padding: 0px 5px;">233</li><li style="box-sizing: border-box;