В настоящее время я работаю над расширением провайдера файлов iOS 11, чтобы перечислять файлы, удаленно хранимые нашей службой.
До сих пор мне удавалось просматривать мою кэшированную базу данных файлов, а также перечисления моего элемента в облаке.
Мой следующий шаг - создание рабочего набора, но до сих пор я не добился успеха при перечислении системы с моим перечислителем рабочего набора. Перечислитель создается, но никогда не перечисляется, перечисляет ли он элементы или изменения.
Я работаю с локальной базой данных для своих предметов, отслеживаю lastUsedDate
, tagData
и favoriteRank
. Они еще не синхронизируются между устройствами, но это не должно помешать локальному устройству отображать эти элементы.
Каждый раз, когда мое хост-приложение отображает файл, оно устанавливает его lastUsedDate
и вызывает signalEnumerator(for: myItemIdentifier)
и signalEnumerator(for: .workingSet)
.
Мой подкласс NSFileProviderExtension
также реализует setTagData(...)
, setFavoriteRank(...)
и setLastUsedDate(...)
.
У меня есть специальный класс для перечисления через рабочий набор следующим образом:
class WorkingSetEnumerator: NSObject, NSFileProviderEnumerator {
let items: [NSFileProviderItem]
// Initialise with the workings set items, might not be correct but should work as first step
init(items: [NSFileProviderItem]) {
self.items = items
super.init()
}
func invalidate() {
// Empty since it is a "dummy" implementation
}
func enumerateItems(for observer: NSFileProviderEnumerationObserver, startingPage page: NSFileProviderPage) {
observer.didEnumerate(self.items)
observer.finishEnumerating(upTo: nil)
}
func enumerateChanges(for observer: NSFileProviderChangesObserver, from anchor: NSFileProviderSyncAnchor) {
//TODO: Implement!
fatalError("Not Implemented, yet!")
}
}
Ничего особенного здесь нет. Здесь для примера он инициализирован с фиктивными данными, но я также пытался использовать живые данные и та же проблема.
Функция, запрашивающая перечислитель, реализована следующим образом:
Переопределить перечислитель функции (для containerItemIdentifier: NSFileProviderItemIdentifier) throws -> NSFileProviderEnumerator {
if containerItemIdentifier == .rootDirectory {
// return a folder enumerator on the root
} else if containerItemIdentifier == .workingSet {
let items = [DummyItem()]
return WorkingSetEnumerator(items: items)
} else {
// return Folder or File enumerator based on the item
}
}
Вот реализация моего DummyItem:
class DummyFileItem: NSObject, NSFileProviderItem {
var parentItemIdentifier: NSFileProviderItemIdentifier {
return NSFileProviderItemIdentifier.rootContainer
}
var itemIdentifier: NSFileProviderItemIdentifier {
return NSFileProviderItemIdentifier("Dummy")
}
var filename: String {
return "Dummy"
}
var typeIdentifier: String {
return "public.folder"
}
var isShared: Bool {
return true
}
var isTrashed: Bool {
return false
}
var lastUsedDate: Date? {
return Date()
}
var favoriteRank: NSNumber? {
return NSNumber(value: NSFileProviderFavoriteRankUnranked)
}
var tagData: Data? {
return nil
}
var documentSize: NSNumber? {
return NSNumber(value: 0)
}
var childItemCount: NSNumber? {
return NSNumber(value: 0)
}
var isDownloading: Bool {
return false
}
var isDownloaded: Bool {
return true
}
var downloadingError: Error? {
return nil
}
var isUploaded: Bool {
return true
}
var isUploading: Bool {
return false
}
var uploadingError: Error? {
return nil
}
var isMostRecentVersionDownloaded: Bool {
return true
}
var isSharedByCurrentUser: Bool {
return true
}
}
Просто некоторые фиктивные данные, которые должны отображать мой элемент хотя бы на последней вкладке.
Как описано ранее, я также попробовал это с моими локальными элементами, которые содержат реальные данные, и то же самое происходит, перечислитель создается, но не перечисляется.
Есть ли способ принудительно перечислить рабочий набор? Любая идея основана на моем описании того, что может отсутствовать?
Спасибо за ваше время и помощь.