Skip to content

发布到商店 ​

人们在 DesktopEngine 商店里找内容、在浏览器里的桌面上试用,再装进应用。每个版本发布前都要经过自动检查和审核员查看;商店给发布的内容签名,应用安装时核对签名,之后自动更新它。

我们正在逐步向创作者开放商店,目前发布需要邀请。你发布的内容要遵守内容政策和创作者协议,开始之前请先读一读。

成为创作者 ​

发邮件到 creators@desktopengine.app 申请邀请,邮件里请写上:

  • 你的作品的链接(必填)。
  • 你想发布哪类条目:壁纸、小组件、桌面伙伴……
  • 你想要的命名空间。

回信里会有一个邀请码。在 store.desktopengine.app/account 登录,在「创作」一栏里填上邀请码、选好命名空间、接受协议和政策(「成为创作者」)。

命名空间和 id ​

命名空间由 3 到 32 个小写字母、数字和连字符组成。它会和你的作品一起显示,发布之后就不能再改,请慎重选择。

你发布的所有内容的 id 都以 app.desktopengine.<命名空间>. 开头:

json
"id": "app.desktopengine.acme.day-progress"

一个 id 第一次 publish 后就永远是你在商店里的条目:id 代表这个条目、它的各个版本,以及它在用户 Mac 上保存的数据(存储属于 id,更新后保留)。不要在版本之间改 id;新项目的 com.example.… id 要在第一次发布之前改掉。

然后在终端里登录商店,令牌保存在你的 Mac 上:

bash
desktopengine login

发布一个版本 ​

bash
desktopengine publish --test-link
desktopengine publish --submit --copyright original --notes "The first version"

publish 像 pack 一样把包压缩构建,作为你的条目的一个版本上传。第一次会用清单的 name 和 description 填写商店页面;副标题、标签、更多语言和「用生成式 AI 制作」的标注在商店的创作者后台里补充。第一次发布之后,商店页面的修改要审核通过才会显示。

上传后立即检查,有问题时命令打印出来,以状态 1 退出。除了 validate 的规则,还要求:

  • id 在你的命名空间里,version 高于之前发布过的所有版本。
  • 包不超过 100 MB(解压后也是),最多 10,000 个文件,单个文件不超过 48 MB,没有符号链接,只有内容会用到的文件类型(代码、数据和文本、图片、音频、视频、3D 模型、着色器、字体、WebAssembly)。
  • apiVersion 不高于已发布的应用支持的版本:需要更新 API 的内容要等那个版本的应用发布。

版本提交之前一直是草稿,用同一个 version 再次发布会替换上传的包。提交之后,下一次上传要改 version;被拒绝的版本可以用同一个版本号重新上传。

提交审核还需要:

  • --copyright:内容的来源,original、licensed 或 open(用 --copyright-note 写明授权方或许可证)。第一次提交时必须填写。
  • --network-purpose:内容有 network 权限时需要,见下文。
  • 年龄分级高于 4+ 时,分级的原因。

所有选项见命令行。在 CI 里设置 DESKTOPENGINE_TOKEN,不用运行 login。

测试链接 ​

--test-link 会打印一个 desktopengine://install?… 链接。在装了 DesktopEngine 的 Mac 上打开它,就能在审核之前装上这个版本,标为测试,不计入安装数。在那里按用户拿到的方式试一试:它从商店安装,会询问权限;而 dev 运行的内容直接得到声明的所有权限。也可以把链接发给测试者;链接 14 天内有效,随时可以用 publish --test-link 再生成一个。

加上 --debug,链接装上的副本可以用 Safari 网页检查器调试(其他已安装的内容不行),只有你自己能安装。

被拒绝的版本没有测试链接:拒绝时会删掉它们,上传修好的版本后再生成新的。

审核做什么 ​

提交的版本先在审核用的 Mac 上、在应用和浏览器里运行,再交给审核员。

在应用里,按已安装内容的限制运行一分钟。这时 DesktopEngine.systemAudio 听到的是一段像音乐的合成信号,和网页预览一样;DesktopEngine.windows 列出的是审核用的 Mac 自己的窗口。在第 5、30、55 秒截图,浅色模式下时钟是下午,每张之后再截一张深色模式、时钟是晚上的;商店里你的内容的截图就取自这些(小组件和桌面伙伴按它们画出的范围裁剪)。运行时记录每个网络请求、控制台、未捕获的异常和内容消耗的能量:商店会显示能耗,浪费资源的内容可能被拒绝(见性能)。

在浏览器里,用 dev --web 的网页运行时,在 Chrome 和 WebKit(Safari 的引擎)里各运行 35 秒;小组件和桌面伙伴会被悬停、点击和拖动。那里运行的是混淆过的 JavaScript,和商店的网页桌面给出的一样:局部名称被改掉,字符串被编码。

出现下面的情况时,版本会被自动拒绝:

  • 在应用里没有启动,或者抛出未捕获的异常。
  • 连接了 network.domains 以外的地址。
  • 在 Chrome 里没有启动、抛出未捕获的异常、有没人处理的 Promise rejection,或者什么都没显示。商店的大多数访客用 Chrome,内容必须能在那里运行。
  • 代码无法混淆,或者混淆后就不能运行了,例如依赖函数名、类名或者代码自身的文本。

所以提交之前,请在 Chrome 里用 desktopengine dev --web 运行内容,看着终端的输出。审核时浏览器里的请求经过一个只支持 GET 和 HEAD 的代理,请求在那里失败时不能变成异常:像离线时一样捕获错误、继续运行(见网络)。dev --web 也会转发别的方法,内容用到时终端会提示。

其他发现本身不会导致拒绝,而是交给审核员判断,包括:控制台错误、声明了却没用到的域名、用字符串生成代码(eval、new Function)、空白的截图、截图里有密码或付款之类的文字、能耗高、Chrome 的截图和应用里的明显不同、浏览器里的帧率低得多,以及 WebKit 里的问题。

审核员接着查看这些结果和截图,在浏览器里运行这个版本,对照内容政策检查它、它的商店页面和年龄分级。通过的版本立即发布;被拒绝的会收到写明原因的邮件,修好后重新上传、提交。如果你认为决定有误,直接回复那封邮件。

年龄分级 ​

每个版本都有一个年龄分级,即适合的最小年龄,和 App Store 一样分为 4+、9+、13+、16+ 和 18+,每一级允许什么见内容政策。在版本还是草稿或被拒绝时,在创作者后台里选择;新版本沿用上一个版本的分级。

  • 高于 4+ 时要选择原因(暴力、恐怖、粗俗语言……),原因会显示在条目页上。
  • 16+ 和 18+ 还要给审核员写一段说明,讲清内容里有什么,并且只有年满 18 岁的创作者才能选。这两级的条目在商店里默认隐藏,成年人主动打开后才显示。
  • 分级要覆盖内容可能显示的一切,包括随时间变化的内容和从网络获取的内容。

应用只安装和运行符合用户年龄的内容。审核员可以修改分级,并会告诉你原因。

网络用途 ​

有 network 权限的内容要说明用网络做什么。商店在条目页上把它和域名一起显示,所以请写给用户看,例如:

bash
desktopengine publish --submit --network-purpose "Gets the weather for the city you choose from api.example.com"

审核员会把它和内容的实际行为、审核运行记录下的请求对照。网络只能用于声明的域名和说明的用途:不追踪用户,不使用能识别个人的统计,不放广告。更新增加了域名时,应用会重新向用户询问 network 权限。

更新 ​

提高 manifest.json 里的 version,再次发布、提交;每个版本都要审核。已发布的版本不会再变。

  • 已安装的副本自动更新:应用在启动时和每天检查一次。
  • 内容的数据(localStorage、defile://usr/)会保留:新版本要能读旧版本保存的数据。
  • 更新声明了新的权限时,应用会询问这些权限。
  • 需要的 apiVersion 高于用户的应用时,不会向那个应用提供这个更新。
  • 新版本在某台 Mac 上启动失败时,应用会退回之前的版本,不再安装这个版本:请在更高的版本里修复。

下架和撤销 ​

违反内容政策或创作者协议的条目,或者收到有效版权投诉的条目,可能会从商店下架;已经安装的人保留他们的副本。有害的条目或其中的某个版本可能被撤销:商店发布一份签名的撤销清单,所有应用停止运行它,也不能再安装。无论哪种情况都会通知你并说明原因。

SDK 以 Apache License 2.0 发布