{"id":532,"date":"2023-02-25T15:52:19","date_gmt":"2023-02-25T07:52:19","guid":{"rendered":"https:\/\/www.appblog.cn\/?p=532"},"modified":"2023-04-29T20:41:06","modified_gmt":"2023-04-29T12:41:06","slug":"react-native-hot-update-deployment-codepush-ios-compatible","status":"publish","type":"post","link":"https:\/\/www.appblog.cn\/index.php\/2023\/02\/25\/react-native-hot-update-deployment-codepush-ios-compatible\/","title":{"rendered":"React Native\u70ed\u66f4\u65b0\u90e8\u7f72-CodePush\uff08\u9002\u914diOS\uff09"},"content":{"rendered":"<h2>CodePush\u7b80\u4ecb<\/h2>\n<p>CodePush\u662f\u5fae\u8f6f\u63d0\u4f9b\u7684\u4e00\u5957\u7528\u4e8e\u70ed\u66f4\u65b0 React Native \u548c Cordova \u5e94\u7528\u7684\u670d\u52a1\u3002CodePush \u662f\u63d0\u4f9b\u7ed9 React Native \u548c Cordova \u5f00\u53d1\u8005\u76f4\u63a5\u90e8\u7f72\u79fb\u52a8\u5e94\u7528\u66f4\u65b0\u7ed9\u7528\u6237\u8bbe\u5907\u7684\u4e91\u670d\u52a1\u3002CodePush \u4f5c\u4e3a\u4e00\u4e2a\u4e2d\u592e\u4ed3\u5e93\uff0c\u5f00\u53d1\u8005\u53ef\u4ee5\u63a8\u9001\u66f4\u65b0 (JS, HTML, CSS and images)\uff0c\u5e94\u7528\u53ef\u4ee5\u4ece\u5ba2\u6237\u7aef SDK \u91cc\u9762\u67e5\u8be2\u66f4\u65b0\u3002CodePush \u53ef\u4ee5\u8ba9\u5e94\u7528\u6709\u66f4\u591a\u7684\u53ef\u786e\u5b9a\u6027\uff0c\u4e5f\u53ef\u4ee5\u8ba9\u4f60\u76f4\u63a5\u63a5\u89e6\u7528\u6237\u7fa4\u3002\u5728\u4fee\u590d\u4e00\u4e9b\u5c0f\u95ee\u9898\u548c\u6dfb\u52a0\u65b0\u7279\u6027\u7684\u65f6\u5019\uff0c\u4e0d\u9700\u8981\u7ecf\u8fc7\u4e8c\u8fdb\u5236\u6253\u5305\uff0c\u53ef\u4ee5\u76f4\u63a5\u63a8\u9001\u4ee3\u7801\u8fdb\u884c\u5b9e\u65f6\u66f4\u65b0\u3002<\/p>\n<p><!-- more --><\/p>\n<p>\u5b98\u65b9\u6587\u6863\uff1a<a target=\"_blank\" rel=\"noopener\" href=\"http:\/\/microsoft.github.io\/code-push\/docs\/\">http:\/\/microsoft.github.io\/code-push\/docs\/<\/a><\/p>\n<h2>\u5b89\u88c5CodePush\u5ba2\u6237\u7aef\u4e0e\u6ce8\u518c\u8d26\u53f7<\/h2>\n<ul>\n<li>\u5b89\u88c5\u5ba2\u6237\u7aef<\/li>\n<\/ul>\n<pre><code>npm install -g code-push-cli<\/code><\/pre>\n<ul>\n<li>\u67e5\u770b\u7248\u672c<\/li>\n<\/ul>\n<pre><code>code-push -v<\/code><\/pre>\n<ul>\n<li>\u6ce8\u518c\u8d26\u53f7<\/li>\n<\/ul>\n<pre><code>code-push register<\/code><\/pre>\n<p>\u6388\u6743\u767b\u9646\u5e76\u5f97\u5230 access key<\/p>\n<ul>\n<li>\u767b\u9646<\/li>\n<\/ul>\n<pre><code>code-push login<\/code><\/pre>\n<ul>\n<li>\u67e5\u770b\u5f53\u524d\u767b\u5f55\u7528\u6237<\/li>\n<\/ul>\n<pre><code>code-push whoami<\/code><\/pre>\n<ul>\n<li>\u6ce8\u9500<\/li>\n<\/ul>\n<pre><code>code-push logout<\/code><\/pre>\n<ul>\n<li>\u5217\u51fa\u5f53\u524d\u767b\u9646\u4f1a\u8bdd<\/li>\n<\/ul>\n<pre><code>code-push session ls<\/code><\/pre>\n<ul>\n<li>\u5220\u9664\u767b\u5f55\u4f1a\u8bdd<\/li>\n<\/ul>\n<pre><code>code-push session rm &lt;machineName&gt;<\/code><\/pre>\n<h2>\u8bbf\u95ee\u5bc6\u94a5<\/h2>\n<ul>\n<li>\u5047\u5982\u60a8\u4e0d\u60f3\u901a\u8fc7 Github \u6216\u8005 Microsoft \u7b2c\u4e09\u65b9\u6388\u6743\u83b7\u53d6 access key\uff0c\u90a3\u4e48\u53ef\u4ee5\u901a\u8fc7\u547d\u4ee4\u65b9\u5f0f\u751f\u6210\uff0c\u9ed8\u8ba4\u6709\u6548\u671f\u4e3a60\u5929<\/li>\n<\/ul>\n<pre><code>code-push access-key add &quot;VSTS Integration&quot;<\/code><\/pre>\n<ul>\n<li>\u901a\u8fc7 access key \u767b\u5f55<\/li>\n<\/ul>\n<pre><code>code-push login --accessKey &lt;accessKey&gt;<\/code><\/pre>\n<ul>\n<li>\u8bbe\u7f6e\u7528\u6237\u540d\u53ca\u6709\u6548\u671f<\/li>\n<\/ul>\n<pre><code>code-push access-key patch &lt;accessKeyName&gt; --name &quot;new name&quot; --ttl 10d<\/code><\/pre>\n<h2>CodePush\u670d\u52a1\u5668APP\u7ba1\u7406<\/h2>\n<ul>\n<li>\u6dfb\u52a0APP<\/li>\n<\/ul>\n<pre><code>code-push app add &lt;appName&gt;<\/code><\/pre>\n<ul>\n<li>\u5206\u5e73\u53f0\u6dfb\u52a0APP<\/li>\n<\/ul>\n<pre><code>code-push app add MyApp-Android\ncode-push app add MyApp-iOS<\/code><\/pre>\n<ul>\n<li>\u91cd\u547d\u540dAPP<\/li>\n<\/ul>\n<pre><code>code-push app rename &lt;appName&gt; &lt;newAppName&gt;<\/code><\/pre>\n<ul>\n<li>\u5220\u9664APP<\/li>\n<\/ul>\n<pre><code>code-push app rm &lt;appName&gt;<\/code><\/pre>\n<ul>\n<li>\u67e5\u770b\u5f53\u524d\u8d26\u53f7\u4e0bAPP\u5217\u8868<\/li>\n<\/ul>\n<pre><code>code-push app ls<\/code><\/pre>\n<h2>\u90e8\u7f72\u7ba1\u7406<\/h2>\n<p>\u4e00\u4e2aAPP\u540d\u5b57\u9ed8\u8ba4\u5bf9\u5e94\u4e24\u4e2a\u90e8\u7f72\u73af\u5883\uff1a\u751f\u4ea7\u73af\u5883Production\u3001\u6a21\u62df\u6216\u6f14\u793a\u73af\u5883Staging<\/p>\n<ul>\n<li>\u6dfb\u52a0\u90e8\u7f72\u73af\u5883<\/li>\n<\/ul>\n<pre><code>code-push deployment add &lt;appName&gt; &lt;deploymentName&gt;<\/code><\/pre>\n<ul>\n<li>\u5220\u9664\u53ca\u91cd\u547d\u540d\u90e8\u7f72\u73af\u5883<\/li>\n<\/ul>\n<pre><code>code-push deployment rm &lt;appName&gt; &lt;deploymentName&gt;\ncode-push deployment rename &lt;appName&gt; &lt;deploymentName&gt; &lt;newDeploymentName&gt;<\/code><\/pre>\n<ul>\n<li>\u67e5\u770b\u6307\u5b9aAPP\u7684\u90e8\u7f72\u73af\u5883<\/li>\n<\/ul>\n<pre><code>code-push deployment ls &lt;appName&gt; [--displayKeys|-k]<\/code><\/pre>\n<p>-k \u8868\u793a\u663e\u793a Deployment Key<\/p>\n<h2>iOS \u96c6\u6210CodePush\u3001\u6253\u5305\u3001\u53d1\u5e03\u66f4\u65b0<\/h2>\n<p>\u53c2\u8003\uff1a<a target=\"_blank\" rel=\"noopener\" href=\"https:\/\/github.com\/Microsoft\/react-native-code-push\">https:\/\/github.com\/Microsoft\/react-native-code-push<\/a><\/p>\n<p>\u5b89\u88c5\u7ec4\u4ef6<\/p>\n<pre><code>npm install --save react-native-code-push@latest<\/code><\/pre>\n<p>\u94fe\u63a5\u7ec4\u4ef6<\/p>\n<pre><code>\/\/ React Native v0.27+\nreact-native link react-native-code-push<\/code><\/pre>\n<pre><code>\/\/ React Native v0.27-\nrnpm link react-native-code-push<\/code><\/pre>\n<p>\u8fc7\u7a0b\u9700\u8981\u8f93\u5165\u90e8\u7f72\u73af\u5883 key<\/p>\n<p>\u7f16\u8bd1\u4e00\u4e0b\uff0c\u662f\u5426\u6210\u529f\uff1f\u67e5\u770binfo.plist\u662f\u5426\u5305\u542bCodePushDeploymentKey<\/p>\n<p>\u624b\u52a8\u6dfb\u52a0\u4f9d\u8d56\u65b9\u6cd5\u8be6\u89c1\uff1a<a target=\"_blank\" rel=\"noopener\" href=\"https:\/\/github.com\/Microsoft\/react-native-code-push#plugin-installation-ios---manual\">https:\/\/github.com\/Microsoft\/react-native-code-push#plugin-installation-ios&#8212;manual<\/a><\/p>\n<h2>\u4f7f\u7528CodePush\u66f4\u65b0\u7b56\u7565<\/h2>\n<p>\u4f7f\u7528 CodePush \u5305\u88f9\u6839\u7ec4\u4ef6<\/p>\n<pre><code class=\"language-javascript\">\/\/ES6\nimport codePush from &quot;react-native-code-push&quot;;\n\nclass MyApp extends Component {\n}\n\nMyApp = codePush(MyApp);<\/code><\/pre>\n<pre><code class=\"language-javascript\">\/\/ES7\nimport codePush from &quot;react-native-code-push&quot;;\n\n@codePush\nclass MyApp extends Component {\n}<\/code><\/pre>\n<ul>\n<li>\u4f7f\u7528\u66f4\u65b0\u9009\u9879<\/li>\n<\/ul>\n<pre><code class=\"language-javascript\">let codePushOptions = { checkFrequency: codePush.CheckFrequency.ON_APP_RESUME };\n\nclass MyApp extends Component {\n}\n\nMyApp = codePush(CodePushOptions)(MyApp);<\/code><\/pre>\n<ul>\n<li>\u624b\u52a8\u66f4\u65b0\u9009\u9879<\/li>\n<\/ul>\n<pre><code class=\"language-javascript\">let codePushOptions = { checkFrequency: codePush.CheckFrequency.MANUAL };\n\nclass MyApp extends Component {\n    onButtonPress() {\n        codePush.sync({\n            updateDialog: true,\n            installMode: codePush.installMode.IMMEDIATE\n        });\n    }\n\n    render() {\n        &lt;View&gt;\n            &lt;TouchableOpacity onPress={this.onButtonPress}&gt;\n                &lt;Text&gt;Check for updates&lt;\/Text&gt;\n            &lt;\/TouchableOpacity&gt;\n        &lt;\/View&gt;\n    }\n}\n\nMyApp = codePush(CodePushOptions)(MyApp);<\/code><\/pre>\n<blockquote>\n<p>Redux Saga for CodePush\uff1areact-native-code-push-saga<\/p>\n<\/blockquote>\n<h2>\u53d1\u5e03\u66f4\u65b0<\/h2>\n<pre><code>code-push release-react &lt;appName&gt; &lt;platform&gt;\n\ncode-push release-react MyApp ios\ncode-push release-react MyApp-Android android<\/code><\/pre>\n<p>\u81ea\u52a8\u6253\u5305js\u548c\u8d44\u6e90\u6587\u4ef6\u6210bundle\u5e76\u4e14\u4e0a\u4f20\u53d1\u5e03\u5230CodePush\u7684\u670d\u52a1\u5668\u3002<\/p>\n<p>\u4e5f\u53ef\u4ee5\u81ea\u5df1\u6253\u5305\uff1a<\/p>\n<p>react-native bundle &#8211;platform \u5e73\u53f0 &#8211;entry-file \u542f\u52a8\u6587\u4ef6 &#8211;bundle-output \u6253\u5305js\u8f93\u51fa\u6587\u4ef6 &#8211;assets-dest \u8d44\u6e90\u8f93\u51fa\u76ee\u5f55 &#8211;dev \u662f\u5426\u8c03\u8bd5 <\/p>\n<pre><code>react-native bundle --platform android --entry-file index.android.js --bundle-output .\/bundles\/index.android.bundle --dev false<\/code><\/pre>\n<p>\u7136\u540e\u624b\u52a8\u4e0a\u4f20\uff1a<\/p>\n<p>code-push release &lt;\u5e94\u7528\u540d\u79f0&gt; &lt;Bundles\u6240\u5728\u76ee\u5f55&gt; &lt;\u5bf9\u5e94\u7684\u5e94\u7528\u7248\u672c&gt; &#8211;deploymentName \u66f4\u65b0\u73af\u5883 &#8211;description \u66f4\u65b0\u63cf\u8ff0 &#8211;mandatory \u662f\u5426\u5f3a\u5236\u66f4\u65b0<\/p>\n<pre><code>code-push release CodePushDemo .\/bundles\/index.android.bundle 1.2.0 --deploymentName Staging --description &quot;\u652f\u6301\u6587\u7ae0\u7f13\u5b58&quot; --mandatory true<\/code><\/pre>\n<h2>\u591a\u73af\u5883\u90e8\u7f72\u6d4b\u8bd5\u7684\u6b65\u9aa4<\/h2>\n<p>\u5ba2\u6237\u7aef\u7684\u56de\u6eda\u673a\u5236\u53ef\u4ee5\u5bfc\u81f4\u670d\u52a1\u5668\u7aef\u7684\u56de\u6eda\uff1a<code>code-push rollback<\/code><\/p>\n<ul>\n<li>\u53d1\u5e03\u66f4\u65b0\u5230Staging\u73af\u5883\uff1a<code>code-push release-react &lt;appName&gt; &lt;platform&gt;<\/code><\/li>\n<li>\u8fd0\u884cStaging\u7248APP\uff0c\u540c\u6b65\u66f4\u65b0\uff0c\u9a8c\u8bc1\u5176\u662f\u5426\u6b63\u5e38\u5de5\u4f5c<\/li>\n<li>\u4ece\u6f14\u793a\u73af\u5883\u63a8\u8fdb\u5230\u751f\u4ea7\u73af\u5883\uff1acode-push promote<\/li>\n<li>\u8fd0\u884cProduction\u7248APP\uff0c\u540c\u6b65\u66f4\u65b0\uff0c\u9a8c\u8bc1\u5176\u662f\u5426\u6b63\u5e38\u5de5\u4f5c<\/li>\n<\/ul>\n<p>\u6211\u4eec\u6ce8\u610f\u5230\u7b2c2\u6b65\u4e0e\u7b2c4\u6b65\uff0c\u9700\u8981\u751f\u6210\u4e24\u79cdAPP\uff0c\u5176\u5b9e\u53ef\u4ee5\u6574\u5408\uff0c\u4f46\u662f\u5374\u662f\u5206\u5e73\u53f0\u7684\uff0c\u8fd9\u91cc\u4ee5iOS\u4e3a\u4f8b\u3002<\/p>\n<h3>\u914d\u7f6e Debug \u548c Release \u6a21\u5f0f\u5206\u522b\u5bf9\u5e94 Staging \u548c Production \u90e8\u7f72\u73af\u5883<\/h3>\n<p><strong>\u4f7f\u7528 XCode \u914d\u7f6e\u9879\u76ee<\/strong><\/p>\n<ul>\n<li>\n<p>\u5728\u9879\u76ee\u914d\u7f6e\u9879\u4e2d\u9009\u62e9 Info \u9009\u9879<\/p>\n<\/li>\n<li>\n<p>\u627e\u5230 Configurations \u90e8\u5206\uff0c\u70b9\u51fb + \u6309\u94ae\uff0c\u9009\u62e9 Duplicate &quot;Release&quot; Configuration\uff0c\u5e76\u5c06\u65b0\u914d\u7f6e\u9879\u547d\u540d\u4e3a Staging<\/p>\n<\/li>\n<\/ul>\n<p><img decoding=\"async\" src=\"https:\/\/cloud.githubusercontent.com\/assets\/116461\/16101597\/088714c0-331c-11e6-9504-5469d9a59d74.png\" alt=\"image\" \/><\/p>\n<ul>\n<li>\n<p>\u5728\u9879\u76ee\u914d\u7f6e\u9879\u4e2d\u9009\u62e9 Build Settings \u9009\u9879<\/p>\n<\/li>\n<li>\n<p>\u627e\u5230\u5de5\u5177\u680f\u533a\u57df\uff0c\u70b9\u51fb + \u6309\u94ae\uff0c\u9009\u62e9 Add User-Defined Setting<\/p>\n<\/li>\n<\/ul>\n<p><img decoding=\"async\" src=\"https:\/\/cloud.githubusercontent.com\/assets\/116461\/15764165\/a16dbe30-28dd-11e6-94f2-fa3b7eb0c7de.png\" alt=\"image\" \/><\/p>\n<ul>\n<li>\u5c06\u65b0\u7684\u914d\u7f6e\u547d\u540d\u4e3a CODEPUSH_KEY \u5e76\u5c55\u5f00\uff0c\u4e3a Staging \u914d\u7f6e\u6307\u5b9a Staging\u90e8\u7f72\u73af\u5883 key\uff0c\u4e3a Release\u914d\u7f6e\u6307\u5b9a Production\u90e8\u7f72\u73af\u5883 key<\/li>\n<\/ul>\n<p><img decoding=\"async\" src=\"https:\/\/cloud.githubusercontent.com\/assets\/8598682\/16821919\/fc1eac4a-490d-11e6-9b11-128129c24b80.png\" alt=\"image\" \/><\/p>\n<ul>\n<li>\u6253\u5f00\u9879\u76ee\u7684 Info.plist\uff0c\u66f4\u65b0 CodePushDeploymentKey\u503c\u4e3a $(CODEPUSH_KEY)<\/li>\n<\/ul>\n<p><img decoding=\"async\" src=\"https:\/\/cloud.githubusercontent.com\/assets\/116461\/15764252\/3ac8aed2-28de-11e6-8c19-2270ae9857a7.png\" alt=\"image\" \/><\/p>\n<p>\u914d\u7f6e\u4e4b\u540e\uff0cStaging \u7f16\u8bd1\u914d\u7f6e\u7528\u5230\u7684\u662f Staging\u73af\u5883\u7684key\uff0cRelease \u7f16\u8bd1\u914d\u7f6e\u7528\u5230\u7684\u662f Production\u73af\u5883\u7684Key<\/p>\n<h2>CodePush \u63d2\u4ef6\u7684\u4f7f\u7528\u573a\u666f<\/h2>\n<p>CodePush \u63d2\u4ef6\u662f\u7531\u4e24\u90e8\u5206\u7ec4\u6210\uff1a<\/p>\n<ul>\n<li>1\u3001js\u6a21\u5757<\/li>\n<li>2\u3001\u539f\u751fAPI<\/li>\n<\/ul>\n<h3>CodePush \u4f7f\u7528\u573a\u666f<\/h3>\n<p>\u4e0b\u9762\u5217\u51faCodePush\u4e00\u4e9b\u5e38\u7528\u7684\u7528\u6cd5\uff0c\u4f60\u53ef\u4ee5\u9009\u62e9\u4e00\u4e2a\u6216\u8005\u7ec4\u5408\u4f7f\u7528\uff1a<\/p>\n<h4>Silent sync on app start<\/h4>\n<pre><code class=\"language-javascript\">\/\/ Fully silent update which keeps the app in sync with the server, without ever interrupting the end user\nclass MyApp extends Component {\n}\nMyApp = codePush(MyApp);<\/code><\/pre>\n<h4>Silent sync everytime the app resumes<\/h4>\n<pre><code class=\"language-javascript\">\/\/ Sync for updates everytime the app resumes.\nclass MyApp extends Component {\n}\nMyApp = codePush({\n    checkFrequency: codePush.CheckFrequency.ON_APP_RESUME,\n    installMode: codePush.InstallMode.ON_NEXT_RESUME\n})(MyApp);<\/code><\/pre>\n<h4>Interactive<\/h4>\n<pre><code class=\"language-javascript\">\/\/ Active update, which lets the end user know about each update, and displays it to them immediately after downloading it\nclass MyApp extends Component {\n}\nMyApp = codePush({\n    updateDialog: true,\n    installMode: codePush.InstallMode.IMMEDIATE\n})(MyApp);<\/code><\/pre>\n<h4>Log\/display progress<\/h4>\n<pre><code class=\"language-java\">\/\/ Make use of the event hooks to keep track of the different stages of the sync process.\nclass MyApp extends Component {\n    codePushStatusDidChange(status) {\n        switch(status) {\n            case codePush.SyncStatus.CHECKING_FOR_UPDATE:\n                console.log(&quot;Checking for updates.&quot;);\n                break;\n            case codePush.SyncStatus.DOWNLOADING_PACKAGE:\n                console.log(&quot;Downloading package.&quot;);\n                break;\n            case codePush.SyncStatus.INSTALLING_UPDATE:\n                console.log(&quot;Installing update.&quot;);\n                break;\n            case codePush.SyncStatus.UP_TO_DATE:\n                console.log(&quot;Installing update.&quot;);\n                break;\n            case codePush.SyncStatus.UPDATE_INSTALLED:\n                console.log(&quot;Update installed.&quot;);\n                break;\n        }\n    }\n\n    codePushDownloadDidProgress(progress) {\n        console.log(progress.receivedBytes + &quot; of &quot; + progress.totalBytes + &quot; received.&quot;);\n    }\n}\nMyApp = codePush(MyApp);<\/code><\/pre>\n<blockquote>\n<p>NOTE: While Apple&#8217;s developer agreement fully allows performing over-the-air updates of JavaScript and assets (which is what enables CodePush!), it is against their policy for an app to display an update prompt. Because of this, we recommend that App Store-distributed apps don&#8217;t enable the updateDialog option when calling sync, whereas Google Play and internally distributed apps (e.g. Enterprise, Fabric, HockeyApp)<\/p>\n<\/blockquote>\n<h3>CodePush \u5c5e\u6027\u53ca\u56de\u8c03\u65b9\u6cd5<\/h3>\n<h4>CodePushOptions \u9009\u9879\u5bf9\u8c61<\/h4>\n<p>CodePushOptions \u9009\u9879\u5bf9\u8c61\u53ef\u4ee5\u81ea\u5b9a\u4e49\uff0c\u5176\u53c2\u6570\u5305\u62ec\uff1a<\/p>\n<p>\uff081\uff09checkFrequency (codePush.CheckFrequency)<\/p>\n<p>\u68c0\u67e5\u9891\u7387\uff0c\u5176\u503c\u5305\u62ec\uff1a<\/p>\n<ul>\n<li>codePush.CheckFrequency.ON_APP_START (0)\uff08\u9ed8\u8ba4\uff09<\/li>\n<li>codePush.CheckFrequency.ON_APP_RESUME (1)<\/li>\n<li>codePush.CheckFrequency.MANUAL (2) <\/li>\n<\/ul>\n<p>\uff082\uff09deploymentKey (String)<\/p>\n<p>\u90e8\u7f72\u73af\u5883 key<\/p>\n<p>\uff083\uff09installMode (codePush.InstallMode)<\/p>\n<p>\u53ef\u9009\u7684\u5b89\u88c5\u6a21\u5f0f\uff0c\u5176\u503c\u5305\u62ec\uff1a<\/p>\n<ul>\n<li>codePush.InstallMode.IMMEDIATE (0)\uff08\u9ed8\u8ba4\uff09<\/li>\n<li>codePush.InstallMode.ON_NEXT_RESTART (1)<\/li>\n<li>codePush.InstallMode.ON_NEXT_RESUME (2)<\/li>\n<\/ul>\n<p>\uff084\uff09mandatoryInstallMode (codePush.InstallMode)<\/p>\n<p>\u5f3a\u5236\u6027\u7684\u5b89\u88c5\u6a21\u5f0f\uff0c\u5176\u503c\u5305\u62ec\uff1a<\/p>\n<ul>\n<li>codePush.InstallMode.IMMEDIATE (0)\uff08\u9ed8\u8ba4\uff09<\/li>\n<li>codePush.InstallMode.ON_NEXT_RESTART (1)<\/li>\n<li>codePush.InstallMode.ON_NEXT_RESUME (2)<\/li>\n<\/ul>\n<p>\uff085\uff09minimumBackgroundDuration (Number)<\/p>\n<p>\u53ea\u5728 InstallMode.ON_NEXT_RESUME \u5b89\u88c5\u6a21\u5f0f\u4e0b\u6709\u6548\uff0c\u8bbe\u7f6e\u66f4\u65b0\u751f\u6548\u7684\u65f6\u95f4\u95f4\u9694\uff0c\u5355\u4f4d\u4e3a\u79d2<\/p>\n<p>\uff086\uff09updateDialog (UpdateDialogOptions)<\/p>\n<p>\u66f4\u65b0\u5f39\u7a97\uff0c\u5305\u542b\u9009\u9879\uff1a<\/p>\n<ul>\n<li>appendReleaseDescription (Boolean) &#8211; false<\/li>\n<li>descriptionPrefix (String) &#8211; &quot; Description: &quot;<\/li>\n<li>mandatoryContinueButtonLabel (String) &#8211; &quot;Continue&quot;<\/li>\n<li>mandatoryUpdateMessage (String) &#8211; &quot;An update is available that must be installed.&quot;<\/li>\n<li>optionalIgnoreButtonLabel (String) &#8211; &quot;Ignore&quot;<\/li>\n<li>optionalInstallButtonLabel (String) &#8211; &quot;Install&quot;<\/li>\n<li>optionalUpdateMessage (String) &#8211; &quot;An update is available. Would you like to install it?&quot;<\/li>\n<li>title (String) &#8211; &quot;Update available&quot;<\/li>\n<\/ul>\n<h4>codePushStatusDidChange<\/h4>\n<p>codePushStatusDidChange (event hook)<\/p>\n<p>status code \u4ea7\u751f\u53d8\u5316\u7684\u56de\u8c03\uff0cSyncStatus \u6240\u6709\u503c\uff1a<\/p>\n<ul>\n<li>codePush.SyncStatus.CHECKING_FOR_UPDATE (0)<\/li>\n<li>codePush.SyncStatus.AWAITING_USER_ACTION (1)<\/li>\n<li>codePush.SyncStatus.DOWNLOADING_PACKAGE (2)<\/li>\n<li>codePush.SyncStatus.INSTALLING_UPDATE (3)<\/li>\n<li>codePush.SyncStatus.UP_TO_DATE (4)<\/li>\n<li>codePush.SyncStatus.UPDATE_IGNORED (5)<\/li>\n<li>codePush.SyncStatus.UPDATE_INSTALLED (6)<\/li>\n<li>codePush.SyncStatus.SYNC_IN_PROGRESS (7)<\/li>\n<li>codePush.SyncStatus.UNKNOWN_ERROR (-1)<\/li>\n<\/ul>\n<h4>codePushDownloadDidProgress<\/h4>\n<p>codePushDownloadDidProgress (event hook)<\/p>\n<p>\u66f4\u65b0\u4e0b\u8f7d\u8fc7\u7a0b\u56de\u8c03\uff0c\u5305\u542b\u53c2\u6570\uff1a<\/p>\n<ul>\n<li>totalBytes (Number)<\/li>\n<li>receivedBytes (Number)<\/li>\n<\/ul>\n<h2>\u5b9e\u9a8c\u8c03\u8bd5<\/h2>\n<p>\u6548\u679c\uff1a\u7a0b\u5e8f\u5458\u89c6\u89d2\u3001\u7ec8\u7aef\u7528\u6237\u89c6\u89d2<\/p>\n<blockquote>\n<p>\u62a5\u9519\uff1aThe uploaded package is identical to the contents of the specified deployment&#8217;s current release  \u8868\u793a\uff1a\u5df2\u7ecf\u5b58\u5728\u4e0e\u8fd9\u6b21\u4e0a\u4f20\u5b8c\u5168\u4e00\u6837\u7684bundle(\u5bf9\u5e94\u4e00\u4e2a\u7248\u672c\u6709\u4e24\u4e2abundle\u7684md5\u5b8c\u5168\u4e00\u6837)\uff0c\u90a3\u4e48CodePush\u4f1a\u62d2\u7edd\u6b64\u6b21\u66f4\u65b0\u3002<\/p>\n<\/blockquote>\n<p>index.ios.js<\/p>\n<pre><code class=\"language-javascript\">\/**\n * Sample React Native App\n * https:\/\/github.com\/facebook\/react-native\n * @flow\n *\/\n\nimport React, { Component } from &#039;react&#039;;\nimport {\n    AppRegistry,\n    StyleSheet,\n    Alert,\n    Text,\n    Image,\n    View\n} from &#039;react-native&#039;;\n\nimport codePush from &quot;react-native-code-push&quot;;\n\nclass CodePushDemo extends Component {\n    codePushStatusDidChange(status) {\n        switch (status) {\n        case codePush.SyncStatus.CHECKING_FOR_UPDATE:\n            console.log(&quot;Checking for updates.&quot;);\n            break;\n        case codePush.SyncStatus.DOWNLOADING_PACKAGE:\n            console.log(&quot;Downloading package.&quot;);\n            break;\n        case codePush.SyncStatus.INSTALLING_UPDATE:\n            console.log(&quot;Installing update.&quot;);\n            break;\n        case codePush.SyncStatus.UP_TO_DATE:\n            console.log(&quot;Installing update.&quot;);\n            break;\n        case codePush.SyncStatus.UPDATE_INSTALLED:\n            console.log(&quot;Update installed.&quot;);\n            break;\n        }\n    }\n\n    codePushDownloadDidProgress(progress) {\n        console.log(progress.receivedBytes + &quot; of &quot; + progress.totalBytes + &quot; received.&quot;);\n    }\n\n    componentDidMount() {\n        console.log(&#039;\u7ec4\u4ef6\u52a0\u8f7d\u540e\u6267\u884c&#039;);\n        \/\/\u8bbf\u95ee\u6162\uff0c\u4e0d\u7a33\u5b9a\n        codePush.checkForUpdate().then((update) =&gt; {\n            if (!update) {\n                Alert.alert(&quot;\u63d0\u793a&quot;, &quot;\u5df2\u662f\u6700\u65b0\u7248\u672c&quot;, [ {\n                    text: &quot;Ok&quot;, onPress: () =&gt; {\n                        console.log(&quot;\u6700\u65b0\u7248\u672c\u786e\u5b9a&quot;);\n                    }\n                }]);\n            } else {\n                codePush.sync({ updateDialog: true, installMode: codePush.InstallMode.IMMEDIATE });\n            }\n        });\n    }\n\n    render() {\n        return (\n            &lt;View style={styles.container}&gt;\n                &lt;Text style={styles.welcome}&gt;\n                    Welcome to React Native!\n                &lt;\/Text&gt;\n                &lt;Text style={styles.instructions}&gt;\n                    To get started, edit index.android.js\n                &lt;\/Text&gt;\n                &lt;Text style={styles.instructions}&gt;\n                    Double tap R on your keyboard to reload,{&#039;\\n&#039;}\n                    Shake or press menu button for dev menu\n                &lt;\/Text&gt;\n                &lt;Image\n                    style={styles.img}\n                    resizeMode=&quot;contain&quot;\n                    source={require(&#039;.\/rnapp.png&#039;)}\n                    \/&gt;\n                &lt;Text style={styles.author}&gt;Powered by RNAPP.CC&lt;\/Text&gt;\n            &lt;\/View&gt;\n        );\n    }\n}\n\nCodePushDemo = codePush(CodePushDemo);\n\nconst styles = StyleSheet.create({\n    container: {\n        flex: 1,\n        justifyContent: &#039;center&#039;,\n        alignItems: &#039;center&#039;,\n        backgroundColor: &#039;#F5FCFF&#039;,\n    },\n    welcome: {\n        fontSize: 20,\n        textAlign: &#039;center&#039;,\n        margin: 10,\n    },\n    instructions: {\n        textAlign: &#039;center&#039;,\n        color: &#039;#333333&#039;,\n        marginBottom: 5,\n    },\n    img: {\n        height: 60,\n        width: 332,\n        marginTop: 20,\n    },\n    author: {\n        justifyContent: &#039;flex-end&#039;,\n        alignItems: &#039;center&#039;,\n        marginBottom: 10,\n        marginTop: 50,\n        textAlign: &#039;center&#039;,\n        fontSize: 16,\n        color: &#039;#3BC1FF&#039;,\n    },\n});\n\nAppRegistry.registerComponent(&#039;CodePushDemo&#039;, () =&gt; CodePushDemo);<\/code><\/pre>\n","protected":false},"excerpt":{"rendered":"<p>CodePush\u7b80\u4ecb CodePush\u662f\u5fae\u8f6f\u63d0\u4f9b\u7684\u4e00\u5957\u7528\u4e8e\u70ed\u66f4\u65b0 React Native \u548c Cordova [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[163],"tags":[],"class_list":["post-532","post","type-post","status-publish","format-standard","hentry","category-react-native"],"_links":{"self":[{"href":"https:\/\/www.appblog.cn\/index.php\/wp-json\/wp\/v2\/posts\/532","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.appblog.cn\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.appblog.cn\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.appblog.cn\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.appblog.cn\/index.php\/wp-json\/wp\/v2\/comments?post=532"}],"version-history":[{"count":0,"href":"https:\/\/www.appblog.cn\/index.php\/wp-json\/wp\/v2\/posts\/532\/revisions"}],"wp:attachment":[{"href":"https:\/\/www.appblog.cn\/index.php\/wp-json\/wp\/v2\/media?parent=532"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.appblog.cn\/index.php\/wp-json\/wp\/v2\/categories?post=532"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.appblog.cn\/index.php\/wp-json\/wp\/v2\/tags?post=532"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}