在您的服务器上托管更新

编辑页面


For the complete documentation index, see llms.txt. Use this Use this file to discover all available pages.

这篇文档已于 2022 年 8 月归档,之后将不再更新。请改用 EAS Update。了解更多

通常情况下,当启用更新时,你的应用会从 Expo 的 CDN 获取包含 JavaScript bundle 和资源的更新。不过,在某些情况下,你可能希望将 JS bundle 和资源托管在你自己的服务器上。例如,在一些屏蔽了 AWS 和 Google Cloud 上 Expo CDN 提供商的国家/地区,更新会很慢或无法使用。在这些情况下,你可以把更新托管到你自己的服务器上,以更好地适配你的使用场景。

为了简单起见,本文其余部分将以为 Android 平台托管更新为例,不过你也可以在任何时候把 Android 替换为 iOS,所有内容依然适用。

导出更新

首先,你需要导出更新的所有静态文件,以便它们可以从你的 CDN 提供服务。为此,请在项目目录中运行 expo export --public-url <server-endpoint>,它会将你应用的所有静态文件输出到名为 dist 的目录中。在本指南中,我们将使用 https://expo.github.io/self-hosting-example 作为示例服务器端点。资源文件和 bundle 文件会根据其内容的 MD5 哈希值命名。此时你的输出目录应该大致如下所示:

.
android-index.json
ios-index.json
assets
  1eccbc4c41d49fd81840aef3eaabe862
bundles
  android-01ee6e3ab3e8c16a4d926c91808d5320.js
  ios-ee8206cc754d3f7aa9123b7f909d94ea.js

托管你的静态文件

当你导出更新的静态文件后,就可以把这些内容托管到你自己的服务器上。例如,在你的 dist 输出目录中,一种简单的托管方式是把内容推送到 GitHub。你可以启用 GitHub Pages 让你的应用可通过类似 https://username.github.io/project-name 这样的基础 URL 访问。如果要在 GitHub 上托管文件,你可以这样做:

Terminal
# 从你的项目目录运行此命令
expo export --public-url https://expo.github.io/self-hosting-example

# 将输出目录中的内容提交到你的仓库
cd dist
git init && git remote add origin git@github.com:expo/self-hosting-example.git
git add * && git commit -m "Update my app with this JS bundle"
git push origin master

要设置一个用于查看你托管更新的二维码,或者如果你想在本地托管文件,请按照下面“在开发中加载二维码/URL”部分中的说明操作。

HTTP headers

在某些托管服务上,例如 AWSFirebase,你需要显式将 JavaScript 文件的 "Content-Type" 头设置为 "application/javascript",这样 更新 才能正常工作。否则 Updates.checkForUpdateAsync() 将失败并报错 "Failed to fetch new update"

下面是一个 firebase.json 配置示例,其中部署目标(deploy target)名为 "native"。

firebase.json
11"hosting": [
22 {
33 "target": "native",
44 "public": "dist",
5 "headers": [
6 {
7 "source": "**/*.js",
8 "headers": [
9 {
10 "key": "Content-Type",
11 "value": "application/javascript"
12 }
13 ]
14 }
15 ]
516 }
617]
718}
Terminal
# 本地导出你的应用
expo export --public-url https://my-app-native.firebaseapp.com/

# 将应用部署到 firebase
firebase deploy --only hosting:native -m "Deploy my app"

构建独立应用

要配置你的独立二进制文件从你的服务器拉取更新,你需要定义一个 URL,用于托管你的 index.json 文件。使用 EAS Build 时,只需在 app.json 中设置 updates.url 属性 指向该 URL 即可。

在开发中加载二维码/URL

你也可以将托管在自己服务器上的更新以二维码/URL 的形式加载到 Expo 移动客户端中,用于开发目的。

二维码:

你用于转换成二维码的 URI 将通过 exps/exp 协议进行深度链接。expsexp 都会深度链接到移动应用,并分别通过 HTTPS 和 HTTP 发起请求。你可以使用在线二维码生成器,输入该 URI 来创建自己的二维码。

下面是一个使用远程服务器的示例:

URI: exps://expo.github.io/self-hosting-example/android-index.json

二维码:使用类似 https://www.qr-code-generator.com/ 的网站生成该 URI。

下面是一个使用 localhost 的示例:

在开发模式下运行 expo export,然后在输出目录中启动一个简单的 HTTP 服务器:

Terminal
# 使用 `ipconfig getifaddr en0` 找到你的本地 IP 地址# 导出静态应用文件
expo export --public-url http://`ipconfig getifaddr en0`:8000 --dev

# 进入你的输出目录
cd dist

# 从输出目录运行一个简单的 http 服务器
python -m SimpleHTTPServer 8000

URI: exp://192.xxx.xxx.xxx:8000/android-index.json(使用类似 ipconfig getifaddr en0 的命令找到你的本地 IP)

二维码:使用类似 https://www.qr-code-generator.com/ 的网站根据你的 URI 生成二维码。

URL

如果你通过传入一个 URL 字符串将更新加载到开发构建中,你需要传入一个指向 JSON manifest 文件的 URL。

下面是一个来自远程服务器的 URL 示例:https://expo.github.io/self-hosting-example/android-index.json

下面是一个来自 localhost 的 URL 示例:http://localhost:8000/android-index.json

高级主题

调试

当 Expo CLI 为你的更新打包时,始终会启用压缩。为了在调试时查看更新的原始源代码,你可以生成 source map。下面是一个示例流程:

  1. 运行 expo export --dump-sourcemap --public-url <your-url>。这也会将你的 bundle sourcemap 导出到 bundles 目录中。
  2. 还会在输出目录的根目录创建一个 debug.html 文件。
  3. 在 Chrome 中,打开 debug.html 并切换到 Source 选项卡。左侧选项卡中应该会有一个资源浏览器,其中有一个红色目录,包含从你的 bundle 重建出的源代码。

调试源代码

资源托管

默认情况下,所有资源都从相对于你的 public-url 解析得到的 assets 路径托管(例如,https://expo.github.io/self-hosting-example/assets)。你可以在 android-index.jsonassetUrlOverride 字段中覆盖此行为。所有相对 URL 都将从 public-url 解析。

特殊字段

index.json 文件中的大多数字段都与 app.json 中的字段相同。下面是一些在 index.json 中比较重要的字段:

  • revisionIdcommitTimepublishedTime:这些字段由 expo export 生成,用于判断是否应该发生更新。
  • bundleUrl:指向应用 bundle 托管路径的 URL。它们也用于判断是否应该发生更新。
  • slug:不应更改。你的应用由 slug 进行命名空间划分,修改此字段会导致 Expo SDK 组件(例如 Filesystem)出现未定义行为。
  • assetUrlOverride:资源托管的路径。默认值为 ./assets,它会相对于你最初传入的基础 public-url 值进行解析。