- 原文地址:iOS File Provider Extension Tutorial
- 原文作者:Ryan Ackermann
- 译文出自:掘金翻译计划
- 本文永久链接:github.com/xitu/gold-m…
- 译者:iWeslie
- 校对者:swants
在本教程中,你将学习 File Provider 拓展以及如何使用它把你 App 的内容公开出来。
File Provider 在 iOS 11 中引入,它通过 iOS 的 文件 App 来访问你 App 管理的内容。同时其他的 App 也可以使用 UIDocumentBrowserViewController
或 UIDocumentPickerViewController
来访问你 App 的数据。
File Provider 拓展的主要任务是:
- 创建表示云端内容的占位文件。
- 当有 App 访问文件内容时先对文件进行下载或上传。
- 在更新文件后发出通知来把更新上传到服务器。
- 枚举存储的文件和目录。
- 对文档执行操作,例如重命名、移动或删除。
你将使用 Heroku 按钮 来配置托管文件的服务器。在服务器设置完成后,你需要配置扩展来对服务器的内容进行枚举。
着手开始
首先,请先 下载资源,完成后找到 Favart-Starter 文件夹并打开 Favart.xcodeproj。确保你已选择 Favart 的 scheme,然后编译并运行该 App,你会看到以下内容:
该 App 提供了一个基础的 View 来告诉用户如何启用 File Provider 扩展,因为你实际上不会在 App 内执行任何操作。每次在本教程中编译运行 App 时,你都将返回主屏幕并打开 文件 这个 App 来访问你的扩展。
注意:如果要在真机上运行该项目,除了为两个 target 设置开发者信息外,还需要在 Configuration 文件夹中编辑 Favart.xcconfig。将 Bundle ID 更新为唯一值。
示例项目将这个值用于两个 target 中 build setting 里的
PRODUCT_BUNDLE_IDENTIFIER
,Provider.entitlements 里的 App Groups 标识符,还有 Info.plist 中的NSExtensionFileProviderDocumentGroup
。在项目中如果没有同步更新它们,你将会得到模糊并且让人没法调试的编译报错信息,而使用自定义的 build settings 将会是一个聪明的方法。
示例项目中已经包含了你将用于 File Provider 扩展的基本组件:
- NetworkClient.swift 包含用于与 Heroku 服务器通信的网络请求客户端。
- FileProviderExtension.swift 就是 File Provider 拓展本身。
- FileProviderEnumerator.swift 包含了枚举器,用于枚举目录的内容。
- Models 是一组用来完成扩展所需的模型。
使用 Heroku 设置后端
首先,你需要一个自己的后端服务器实例。幸运的是,使用 Heroku Button 将很容易完成这个操作。单击下面的按钮访问 Heroku 的 dashboard。
在你注册完 Heroku 的免费账号后,你将看到以下页面:
在此页面上,你可以给你的 App 取一个名字,也可以将该字段留空,Heroku 将为你自动生成一个名称。不必配置其他东西,现在你可以点击 Deploy app 按钮,一会儿之后你的后端就会启动并运行。
在 Heroku 完成部署 App 之后,单击底部的 View。这会跳转到你托管实例的后端 URL。在根目录下,你应该看到一条 JSON 数据,是你熟悉的 Hello world!。
最后,你需要复制 Heroku 实例的 URL,但是只需要其中的域名部分:{app-name}.herokuapp.com。
在 starter 项目中,打开 Provider/NetworkClient.swift。在文件的顶部,你应该会看到一条警告,告诉你 Add your Heroku URL here。删除这个警告并用你的 URL 替换 components.host
占位符字符串。
现在你就完成了服务器配置。接下来,你将定义 File Provider 所依赖的模型。
定义 NSFileProviderItem
首先,File Provider 需要一个遵循了 NSFileProviderItem
协议的模型。此模型将提供有关 File Provider 所管理的文件的信息。starter 项目在 FileProviderItem.swift 中已经定义了 FileProviderItem
,在使用它之前需要遵循一些协议。
虽然该协议含有 27 个属性,但我们只需要其中 4 个。其他一些可选属性为 File Provider 提供有关每个文件的详细信息以及一些其他功能。在本教程中,你将用到以四个属性:itemIdentifier
、parentItemIdentifier
、filename
和 typeIdentifier
。
itemIdentifier
给模型提供了唯一标示符。File Provider 使用 parentIdentifier
来跟踪它在扩展的层次结构中的位置。
filename
是 文件 里显示的 App 名字。typeIdentifier
是一个 统一类型标识符(UTI)。
在 FileProviderItem
可以遵循 NSFileProviderItem
协议之前,它还需要一个处理来自后端数据的方法。MediaItem
定义了一个后端数据的简单模型。我们并不是直接在 FileProviderItem
中使用这个模型,而是使用 MediaItemReference
来处理 File Provider 扩展的一些额外逻辑从而把其中的坑填上。
你将在本教程中使用 MediaItemReference
有两个原因:
- 在 Heroku 上托管的后端非常简洁,它无法提供
NSFileProviderItem
所需的所有信息,因此你需要在其他地方获取它。 - 这个 File Provider 扩展也很简单,更完整的 File Provider 扩展需要使用诸如 Core Data 之类的东西在本地持久化存储后端返回的数据,让它能在该扩展的生命周期结束后引用它。
为了将教程的重心放到 File Provider 扩展本身上,你将使用 MediaItemReference
来快速入门,你需要将四个必填字段嵌入到 URL
对象中。然后将该 URL 编码成 NSFilProviderItemIdentifier
。你不需要手动存储其他东西,因为 NSFileProviderExtension
会为你处理它。
打开 Provider/MediaItemReference.swift 并把以下代码添加到 MediaItemReference
里:
// 1
private let urlRepresentation: URL
// 2
private var isRoot: Bool {
return urlRepresentation.path == "/"
}
// 3
private init(ur