博览会和发布渠道...如何识别dev/prod和真实渠道
Expo and release channels...how to recognise dev/prod and a real channel
我在 expo 发布渠道上遇到了一些问题。
我不是 React Native 和 Expo 的专家,这让事情变得更容易:
如果我使用本地开发环境,则不会设置频道(这是有道理的)。
而且最终发布还是"production"不会有频道集,
这让我很不清楚我应该如何识别 'production' 和 'development'.
然后,如果我想添加一个频道,则会添加一个新的复杂度级别...例如 'staging',它将有一个频道...
锦上添花的是,在我的部署系统(Circle)中,我必须在频道中构建'development'(否则NODE_ENV将是"production")
有人知道如何正确使用频道吗? :)
基本上,我没有找到比这个更好的解决方案:
import { Constants } from 'expo'
const ENV= {production:{},staging:{},development:{}}
// Having fun with channels
const channel = Constants.manifest.releaseChannel;
if (channel === null || channel === undefined || channel === '') {
if (process.env.NODE_ENV === 'production') {
return ENV.production;
}
if (process.env.NODE_ENV === 'development') {
return ENV.development;
}
}
if (channel === 'staging') {
return ENV.staging;
}
if (channel === 'development') {
return ENV.development;
}
return ENV.production;
非常感谢!
我认为你漏掉了什么是发布渠道。
当您的应用程序使用 exp build
构建时,它会绑定到一个发布渠道(默认为 default
)。
稍后,如果您想进行 OTA 更新,只需 运行 exp publish
即可将您的代码发布到发布频道(同样:默认为 default
)。
当您向用户发布独立版本时,您不想通过 OTA 向他们提供未经测试的代码等,因此您希望用户将发布渠道设置为 ex。 prod
.
这与 NODE_ENV 完全不同,我真的看不出将它们捆绑在一起的意义。
值得注意的是,process.env.NODE_ENV === 'production'
构造仅在捆绑构建过程中才有意义 - 捆绑器将是 运行,NODE_ENV
变量设置为特定环境。
在 production
环境中,这意味着捆绑器的内置压缩器会将所有出现的 process.env.NODE_ENV
替换为其实际值 (production
f.e), metro
打包器默认是这样配置 minifier 的。 F.e:
if (process.env.NODE_ENV !== 'production') {
... some dev-only code, like 'assert(something)' or 'console.log(some debug info)'
}
会变成
if ('production' !== 'production') {
... some dev-only code, like 'assert(something)' or 'console.log(some debug info)'
}
然后会进一步缩小到
if (false) {
... some dev-only code, like 'assert(something)' or 'console.log(some debug info)'
}
然后将从结果代码中完全消除,因为 if
语句中的代码无论如何都不会执行。
例如,您的代码在开发模式下将被视为:
if (channel === null || channel === undefined || channel === '') {
if ('development' === 'production') {
return ENV.production;
}
if ('development' === 'development') {
return ENV.development;
}
}
... further simplified to:
if (channel === null || channel === undefined || channel === '') {
return ENV.development;
}
在产品模式下:
if (channel === null || channel === undefined || channel === '') {
if ('production' === 'production') {
return ENV.production;
}
if ('production' === 'development') {
return ENV.development;
}
}
... further simplified to:
if (channel === null || channel === undefined || channel === '') {
return ENV.production;
}
你应该记住,react-native 代码 运行 在设备上的本机应用程序中,而不是在某些 Node
实例中,因此它对严格的节点特定 ecosystem/environment 变量(不过,您可以通过一些库(如 dot-env
等)使用自定义值猴子修补 process.env
),这是 npm
中的某些节点 utils/packages 不能的原因之一不能按原样用于 react-native 应用程序,因为它们是节点特定的 (fs
f.e.).
这与在提供给客户端浏览器的前端代码上使用 process.env.NODE_ENV
变量相同 - 浏览器中没有可用的 process
实例,并且除非您使用缩小器并将其配置为用某些特定值替换 process.env.NODE_ENV
的出现,否则您的代码只会抛出未定义的变量访问错误。 Metro
bundler 为您处理这个特定的用例,但我认为无论如何都值得一提。
我在 expo 发布渠道上遇到了一些问题。 我不是 React Native 和 Expo 的专家,这让事情变得更容易:
如果我使用本地开发环境,则不会设置频道(这是有道理的)。
而且最终发布还是"production"不会有频道集, 这让我很不清楚我应该如何识别 'production' 和 'development'.
然后,如果我想添加一个频道,则会添加一个新的复杂度级别...例如 'staging',它将有一个频道...
锦上添花的是,在我的部署系统(Circle)中,我必须在频道中构建'development'(否则NODE_ENV将是"production")
有人知道如何正确使用频道吗? :)
基本上,我没有找到比这个更好的解决方案:
import { Constants } from 'expo'
const ENV= {production:{},staging:{},development:{}}
// Having fun with channels
const channel = Constants.manifest.releaseChannel;
if (channel === null || channel === undefined || channel === '') {
if (process.env.NODE_ENV === 'production') {
return ENV.production;
}
if (process.env.NODE_ENV === 'development') {
return ENV.development;
}
}
if (channel === 'staging') {
return ENV.staging;
}
if (channel === 'development') {
return ENV.development;
}
return ENV.production;
非常感谢!
我认为你漏掉了什么是发布渠道。
当您的应用程序使用 exp build
构建时,它会绑定到一个发布渠道(默认为 default
)。
稍后,如果您想进行 OTA 更新,只需 运行 exp publish
即可将您的代码发布到发布频道(同样:默认为 default
)。
当您向用户发布独立版本时,您不想通过 OTA 向他们提供未经测试的代码等,因此您希望用户将发布渠道设置为 ex。 prod
.
这与 NODE_ENV 完全不同,我真的看不出将它们捆绑在一起的意义。
值得注意的是,process.env.NODE_ENV === 'production'
构造仅在捆绑构建过程中才有意义 - 捆绑器将是 运行,NODE_ENV
变量设置为特定环境。
在 production
环境中,这意味着捆绑器的内置压缩器会将所有出现的 process.env.NODE_ENV
替换为其实际值 (production
f.e), metro
打包器默认是这样配置 minifier 的。 F.e:
if (process.env.NODE_ENV !== 'production') {
... some dev-only code, like 'assert(something)' or 'console.log(some debug info)'
}
会变成
if ('production' !== 'production') {
... some dev-only code, like 'assert(something)' or 'console.log(some debug info)'
}
然后会进一步缩小到
if (false) {
... some dev-only code, like 'assert(something)' or 'console.log(some debug info)'
}
然后将从结果代码中完全消除,因为 if
语句中的代码无论如何都不会执行。
例如,您的代码在开发模式下将被视为:
if (channel === null || channel === undefined || channel === '') {
if ('development' === 'production') {
return ENV.production;
}
if ('development' === 'development') {
return ENV.development;
}
}
... further simplified to:
if (channel === null || channel === undefined || channel === '') {
return ENV.development;
}
在产品模式下:
if (channel === null || channel === undefined || channel === '') {
if ('production' === 'production') {
return ENV.production;
}
if ('production' === 'development') {
return ENV.development;
}
}
... further simplified to:
if (channel === null || channel === undefined || channel === '') {
return ENV.production;
}
你应该记住,react-native 代码 运行 在设备上的本机应用程序中,而不是在某些 Node
实例中,因此它对严格的节点特定 ecosystem/environment 变量(不过,您可以通过一些库(如 dot-env
等)使用自定义值猴子修补 process.env
),这是 npm
中的某些节点 utils/packages 不能的原因之一不能按原样用于 react-native 应用程序,因为它们是节点特定的 (fs
f.e.).
这与在提供给客户端浏览器的前端代码上使用 process.env.NODE_ENV
变量相同 - 浏览器中没有可用的 process
实例,并且除非您使用缩小器并将其配置为用某些特定值替换 process.env.NODE_ENV
的出现,否则您的代码只会抛出未定义的变量访问错误。 Metro
bundler 为您处理这个特定的用例,但我认为无论如何都值得一提。