你的打包产物里带着你还没宣布的功能的代码,它读起来就像是即将到来的内容的预览。
特性开关名称和路由字符串读起来像更新日志
特性开关名称、路由字符串和未发布的界面文案,读起来就像是写给了错误受众的更新日志。人们会在你多次发布之间对打包产物做差异对比,并写下发生了什么变化。一个名字可读的特性开关,会在你还没有公开说任何事情之前,就被人在开发者工具里打开并截图。
这一切都不需要你的源代码。发送到每一位访客浏览器的打包产物,本身就已经摆在那里,任何想看的人都能看,不管你有没有链接到它。
重新构建对打包产物差异对比意味着什么
identifiers.rename 会重命名你的标识符,strings.encode 会编码你的字面量,因此已发布文件里不存在 newBilling 这样可以搜索的名字,也没有未发布的文案可以引用。每次构建的新 seed 会重塑整个产物,包括没有变化的代码,因此对比两次发布不再是查看有什么新内容的廉价方式。
更有力的答案不是一个 AfterPack 设置项。尚未上线的代码,最好的办法是完全不进入打包产物:一个由服务端决定的开关,或者一个藏在权益检查后面的动态导入,意味着该功能根本不在发布内容里。没有哪个预设能做到这一点,因为产物里已经没有东西可以保护了。
保护留下来的部分,移除不必须留下的部分
对于确实留在打包产物中的代码,可以在整个构建范围内提高预设,或者标记携带未发布功能的那个模块:
/* @afterpack preset=hard */
export function renderNewBillingFlow() {
// unreleased UI
}
/* @afterpack end */先在整个打包产物范围内把 preset 设为 medium 或 hard。提高单个模块的指令需要 Pro。当预设的档位不是你想要的粒度时,complexity 可以直接设置目标值。
确认未发布的模块已被覆盖
打开开启 protectionMap.enabled 后写入的 Protection Map,确认未发布的模块达到了你预期的目标。在你的部署中保持 sourceMap.enabled 关闭:一份公开发布的 map,无论旁边那份文件是用什么预设构建的,都会把你原始的名字和字符串交还回去。
客户端开关依然能做到什么
重命名、编码,以及每次发布都不同的构建形态,意味着打包产物不再读起来像一份更新日志,对比两个版本也不再是入手的廉价方式。一个客户端可以打开的开关,依然可能被仔细阅读新构建的人找到并打开。任何真正处于封锁期的内容,都应该放在一个决定该功能是否运行的服务端响应之后。
下一步
- 预设:从
minify到extreme的阶梯,以及每一档的复杂度目标。 - 指令:在更高预设下还有哪些内容值得标记。
- Protection Map:确认指令是否生效。