JSPatch 從入門到放棄

JSPatch 是什么

JSPatch 是一個開源項目(Github鏈接),只需要在項目里引入極小的引擎文件,就可以使用 JavaScript 調用任何 Objective-C 的原生接口父叙,替換任意 Objective-C 原生方法。目前主要用于下發(fā) JS 腳本替換原生 Objective-C 代碼练俐,實時修復線上 bug注暗。

JSPatch平臺又是什么鬼

JSPatch需要你自己搞一個服務器管理、下發(fā)腳本猫牡,還要處理安全問題胡诗,高并發(fā)問題,煩死你淌友。JSPatch平臺封裝了SDK煌恢,你只需要繼承SDK就可以省去一堆的麻煩。

JSPatch 需要使用者有一個后臺可以下發(fā)和管理腳本震庭,并且需要處理傳輸安全等部署工作瑰抵,JSPatch 平臺幫你做了這些事,提供了腳本后臺托管器联,版本管理二汛,保證傳輸安全等功能婿崭,讓你無需搭建一個后臺,無需關心部署操作肴颊,只需引入一個 SDK 即可立即使用 JSPatch氓栈。

JSPatch 平臺的 SDK 在核心代碼的基礎上增加了向平臺請求腳本/傳輸解密/版本管理等功能,只用于這個平臺婿着。

通過 JSPatch 平臺上傳的腳本文件都會保存在七牛云存儲上授瘦,客戶端 APP 只跟七牛服務器通訊,支持高并發(fā)竟宋,CDN分布全國提完,速度和穩(wěn)定性有保證。

SDK接入

這種問題不要問我袜硫,注冊一個賬號氯葬,建一個app獲取到appid,然后接入SDK完事兒婉陷。至于你是用cocoapods還是手動接入帚称,全憑個人喜好。SDK接入

API主要方法

+startWithAppKey:

傳入在平臺申請的 appKey秽澳,啟動 JSPatch SDK闯睹。在-application:didFinishLaunchingWithOptions:開頭初始化第三方庫的時候一并調用初始化。

+sync

與 JSPatch 平臺后臺同步担神,詢問是否有 patch 更新楼吃,如果有更新會自動下載并執(zhí)行。

每調用一次 +sync 就會請求一次后臺妄讯,如果app啟動的時候檢查一次就OK的話就在-application:didFinishLaunchingWithOptions:調用一次孩锡。

如果實時性要求高,就在-applicationDidBecomeActive:的時候調用亥贸。

+setupLogger:

SDK打一些請求和執(zhí)行的log躬窜,默認是NSLog()輸出,如果app有自己的日志系統(tǒng)炕置,并且希望自己的日志系統(tǒng)拿到這些log荣挨,則在+startWithAppKey之前調用這個方法。

+testScriptInBundle

寫好的腳本上線前總要測試一下吧朴摊,就是用這個方法默垄。需要把main.js文件拖到項目中,并且不要調用+startWithAppKey:方法甚纲。

注意?诙А!=楦恕:測試完成一定要刪除main.js,血淋淋的教訓是鹃操,如果不刪除况既,線上的腳本down下來之后,無法確定會執(zhí)行哪個main.js,莫名其妙的問題组民,并且很難找到。切記切記

+setupCallback:

JSPatch 執(zhí)行過程中的事件回調悲靴,在以下事件發(fā)生時會調用傳入的 block:

typedef NS_ENUM(NSInteger, JPCallbackType){
    JPCallbackTypeUnknow        = 0,
    JPCallbackTypeRunScript     = 1,    //執(zhí)行腳本
    JPCallbackTypeUpdate        = 2,    //腳本有更新
    JPCallbackTypeUpdateDone    = 3,    //已拉取新腳本
    JPCallbackTypeCondition     = 4,    //條件下發(fā)
    JPCallbackTypeGray          = 5,    //灰度下發(fā)
};

例如
[JSPatch setupCallback:^(JPCallbackType type, NSDictionary *data, NSError *error) {
    switch (type) {
        case JPCallbackTypeUpdate: {
            NSLog(@"updated %@ %@", data, error);
            break;
        }
        case JPCallbackTypeRunScript: {
            NSLog(@"run script %@ %@", data, error);
            break;
        }
        default:
            break;
    }
}];

+setupUserData:

定義用戶屬性臭胜,在+sync:之前調用,用于條件下發(fā)癞尚,可以用來做AB測試耸三。什么是AB測試?自己去Google啊...

[JSPatch setupUserData:@{
    @"userId": user.userId, 
    @"location": user.location,
    @"gender":user.gender,
    @"age":user.age
}];
條件下發(fā)
條件下發(fā)

發(fā)布補丁的時候選擇條件下發(fā)浇揩,寫入相應的條件就可以實現條件下發(fā)仪壮。例如圖中性別是女,年齡小于35歲的用戶顯示特定的內容胳徽。還可以選擇手機系統(tǒng)的版本积锅。

+setupDevelopment

開發(fā)者預覽模式,可以在 debug 模式下測試補丁效果养盗。

[JSPatch startAppWithKey:@""];
#ifdef DEBUG
[JSPatch setupDevelopment];
#endif
[JSPatch sync];

灰度下發(fā)

這個功能太實用了缚陷,選擇灰度下發(fā)可以按照比例灰度人數灰度下發(fā)。比例灰度例如隨機挑選 30% 的設備生效往核;人數灰度比如只安裝1000臺設備箫爷。應用場景:

  1. 先下發(fā)一批看看效果,如果OK就全量下發(fā)
  2. 只對部分用戶下發(fā)聂儒,顯示特定的效果(和條件下發(fā)類似)

實戰(zhàn)

扯了這么多終于到實戰(zhàn)了虎锚。

背景:

  • 項目已經集成了SDK
  • 注冊過了平臺賬號
  • 已經注冊了APP獲得了appkey
  • 已經上線了集成過JSPatch SDK的app
  • 這個上線的版本出現了大量的crash,crash率很高衩婚,不馬上解決窜护,老板就會馬上解決你...

線上的代碼是這樣的,數組訪問越界了

@implementation DSHomeViewController

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
  NSString *content = self.dataSource[[indexPath row]]; //可能會超出數組范圍導致crash
  DSGoodsViewController *controller = [[DSGoodsViewController alloc] initWithContent:content];
  [self.navigationController pushViewController:controller];
}

@end

修改源代碼

修改后的代碼

@implementation DSHomeViewController

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
  if(self.dataSource.length > indexPath.row){
    NSString *content = self.dataSource[indexPath.row]; 
    DSGoodsViewController *controller = [[DSGoodsViewController alloc] initWithContent:content];
    [self.navigationController pushViewController:controller];
  }
}

@end

編寫補丁腳本

打開JSPatch代碼轉換器,原生代碼轉化為JS代碼

轉化器
轉化器

轉化成功了谅猾,但是要數組柄慰,需要修改一下。常見問題 修改之后的腳本,為了能夠知道腳本運行税娜,第一行加上log

console.log('JSPatch Run Success');
require("DSGoodsViewController");

defineClass("DSHomeViewController", {
    tableView_didSelectRowAtIndexPath: function(tableView, indexPath) {
        var row = indexPath.row();
        if (self.dataSource().length() > row) {
            var content = self.dataSource()[row];
            var controller = DSGoodsViewController.alloc().initWithContent(content);
            self.navigationController().pushViewController(controller);
        }
    }
}, {});

測試腳本

寫好之后的腳本存為main.js放到項目中坐搔,在-application:didFinishLaunchingWithOptions:方法中打開測試

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
     //[JSPatch startWithAppKey:myAPPKey];
    //[JSPatch sync];
    [JSPatch testScriptInBundle];
    ….
}

編譯運行會看到控制臺log輸出JSPatch Run Success 然后......怎么能少了調試呢

在Safari中斷點調試

開啟 Safari 調試菜單

Safari -> 偏好設置 -> 高級 -> 勾選[在菜單欄中顯示“開發(fā)”菜單]

啟動app進行調試

啟動APP -> Safari -> 開發(fā) -> 選擇你的機器 -> JSContext

在 iOS8 下,JSPatch 支持使用 Safari 自帶的調試工具對 JS 腳本進行斷點調試敬矩,界面大致長這樣


JS調試器
JS調試器

上傳腳本

  1. 在平臺上新建一個線上的版本
  2. 把調試通過的腳本main.js上傳到這個線上的版本
  3. 選擇全量下發(fā)(因為要搞定crash)
  4. 刪除本地的main.js
  5. 好了概行,等著下發(fā)之后crash率降下來,飯碗保住了

常見的問題

  1. 不能用 NSLog('xx')弧岳,應該用 console.log('xx')
  2. get property 記得加括號凳忙,例如 self.navigationItem()业踏,而不是 self.navigationItem
  3. 私有成員變量要用 self.valueForKey()self.setValue_forKey() 接口存取
  4. block 里不能直接使用 self,應該在block外定義var myself = self;

其他更多請參見 wiki 的 基礎用法常見問題

未完待續(xù)。涧卵。勤家。

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市柳恐,隨后出現的幾起案子伐脖,更是在濱河造成了極大的恐慌,老刑警劉巖乐设,帶你破解...
    沈念sama閱讀 207,113評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件讼庇,死亡現場離奇詭異,居然都是意外死亡近尚,警方通過查閱死者的電腦和手機蠕啄,發(fā)現死者居然都...
    沈念sama閱讀 88,644評論 2 381
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來戈锻,“玉大人歼跟,你說我怎么就攤上這事〔芭妫” “怎么了嘹承?”我有些...
    開封第一講書人閱讀 153,340評論 0 344
  • 文/不壞的土叔 我叫張陵,是天一觀的道長如庭。 經常有香客問我叹卷,道長,這世上最難降的妖魔是什么坪它? 我笑而不...
    開封第一講書人閱讀 55,449評論 1 279
  • 正文 為了忘掉前任骤竹,我火速辦了婚禮,結果婚禮上往毡,老公的妹妹穿的比我還像新娘蒙揣。我一直安慰自己,他們只是感情好开瞭,可當我...
    茶點故事閱讀 64,445評論 5 374
  • 文/花漫 我一把揭開白布懒震。 她就那樣靜靜地躺著,像睡著了一般嗤详。 火紅的嫁衣襯著肌膚如雪个扰。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 49,166評論 1 284
  • 那天葱色,我揣著相機與錄音递宅,去河邊找鬼。 笑死,一個胖子當著我的面吹牛办龄,可吹牛的內容都是我干的烘绽。 我是一名探鬼主播,決...
    沈念sama閱讀 38,442評論 3 401
  • 文/蒼蘭香墨 我猛地睜開眼俐填,長吁一口氣:“原來是場噩夢啊……” “哼安接!你這毒婦竟也來了?” 一聲冷哼從身側響起英融,我...
    開封第一講書人閱讀 37,105評論 0 261
  • 序言:老撾萬榮一對情侶失蹤赫段,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后矢赁,有當地人在樹林里發(fā)現了一具尸體,經...
    沈念sama閱讀 43,601評論 1 300
  • 正文 獨居荒郊野嶺守林人離奇死亡贬丛,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 36,066評論 2 325
  • 正文 我和宋清朗相戀三年撩银,在試婚紗的時候發(fā)現自己被綠了。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片豺憔。...
    茶點故事閱讀 38,161評論 1 334
  • 序言:一個原本活蹦亂跳的男人離奇死亡额获,死狀恐怖,靈堂內的尸體忽然破棺而出恭应,到底是詐尸還是另有隱情抄邀,我是刑警寧澤,帶...
    沈念sama閱讀 33,792評論 4 323
  • 正文 年R本政府宣布昼榛,位于F島的核電站境肾,受9級特大地震影響,放射性物質發(fā)生泄漏胆屿。R本人自食惡果不足惜奥喻,卻給世界環(huán)境...
    茶點故事閱讀 39,351評論 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望非迹。 院中可真熱鬧环鲤,春花似錦、人聲如沸憎兽。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,352評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽纯命。三九已至西剥,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間扎附,已是汗流浹背蔫耽。 一陣腳步聲響...
    開封第一講書人閱讀 31,584評論 1 261
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人匙铡。 一個月前我還...
    沈念sama閱讀 45,618評論 2 355
  • 正文 我出身青樓图甜,卻偏偏與公主長得像,于是被迫代替她去往敵國和親鳖眼。 傳聞我的和親對象是個殘疾皇子黑毅,可洞房花燭夜當晚...
    茶點故事閱讀 42,916評論 2 344

推薦閱讀更多精彩內容

  • 背景介紹 IOS平臺提交審核的周期太長,快則45天钦讳,慢則半個月或者20天矿瘦,如果碰到圣誕節(jié)等假日,可能一個月都有可能...
    恒源賓館閱讀 2,233評論 10 27
  • JSPatch 是騰訊微信團隊牛人bang開源的一種通過JavaScript調用iOS原生代碼來實現熱修復或者動態(tài)...
    杭研融合通信iOS閱讀 841評論 2 23
  • JSPatch作為熱更新技術的黑科技愿卒,已經不是什么前沿的新聞了缚去,像騰訊、美團等大公司也在使用JSPatch琼开。前段時...
    任爾東西南北瘋閱讀 1,488評論 0 3
  • JSPatch簡介 JSPatch 是一個開源項目(Github鏈接)易结,只需要在項目里引入極小的引擎文件,就可以使...
    zyl04401閱讀 2,169評論 0 6
  • 最近接觸到熱修復, 確實能解燃眉之急, 非常好用, 故分享給大家. 這里只講 JSPatch, 這個是現在最熱門最...
    Cean16閱讀 1,444評論 2 4