在应用程序及其共享扩展中使用 SwiftData 和共享 SQLite 数据库。如果您仅在 Safari 中点击“共享”,并且会显示扩展程序,那么当您激活应用程序时,一个视图会抛出:
DraftsView:getDrafts():线程 1:致命错误:“尝试!”表达式意外引发错误:Error Domain=NSCocoaErrorDomain Code=256“无法打开文件“default.store”。” UserInfo={NSFilePath=/private/var/mobile/Containers/Shared/AppGroup/455BCEA6-209A-41EA-852D-0488375BD111/Library/Application Support/default.store,NSSQLiteErrorDomain=1}
错误:-executeRequest:遇到异常 = /private/var/mobile/Containers/Shared/AppGroup/455BCEA6-209A-41EA-852D-0488375BD111/Library/Application Support/default.store 数据库的 I/O 错误。 SQLite 错误代码:1,'没有这样的表:ZDRAFT' with userInfo = { NSFilePath =“/private/var/mobile/Containers/Shared/AppGroup/455BCEA6-209A-41EA-852D-0488375BD111/Library/Application Support/default.store”; NSSQLiteErrorDomain = 1; }
该视图的所有项目均未打开。由于视图保存了模型上下文,因此所有这些项目都将显示为永久删除。
奇怪的是主视图不受影响。
为了避免并发问题,应用程序或共享扩展中都没有 @Query 变量,仅根据需要获取。
失败视图的 SwiftData 模型:
@Model final class ClassA {
@Attribute(.unique)
var id: String
@Relationship(deleteRule: .cascade, inverse: \ClassB.parent)
var things: [ClassB] = [ClassB]()
}
@Model final class ClassB {
@Attribute(.unique)
var id: String
// Inverse link to parent
var parent: ClassA?
@Relationship(deleteRule: .cascade, inverse: \ClassC.parent)
var otherThings: [ClassC] = [ClassC]()
}
@Model final class ClassC {
@Attribute(.unique)
var id: String
// Inverse link to parent
var parent: ClassB?
}
对于不受影响的视图:
@Model final class Item {
@Attribute(.unique)
var id: UUID
var itemUrl: String
}
共享扩展都是一个 Swift 类:
class ShareViewController: SLComposeServiceViewController {
private let modelContainer: ModelContainer
private let modelContext: ModelContext
required init?(coder: NSCoder) {
do {
modelContainer = try ModelContainer(for: SavedItem.self, configurations: ModelConfiguration(isStoredInMemoryOnly: false))
} catch {
fatalError("Failed to create the model container: \(error)")
}
modelContext = modelContainer.mainContext
super.init(coder: coder)
}
[…]
func saveItem(itemUrl: String) {
var fetch = FetchDescriptor<Item>(
predicate: #Predicate { item in item.itemUrl == itemUrl }
)
fetch.includePendingChanges = true
let dupes = try? modelContext.fetch(fetch)
guard dupes?.count == 0 else { return }
let id = UUID()
let item = Item(id: id)
modelContext.insert(item)
do {
try modelContext.save()
} catch(let error) {
print("error: \(error.localizedDescription)")
}
}
}
尝试过模特演员,是个崩溃的毛球。
如果您从未在 Safari 中查看共享扩展程序图标,应用程序可以正常工作。
有人有有效的 SwiftData 共享扩展示例代码吗?
将崩溃的数据模型类添加到架构参数中修复了它:
let config = ModelConfiguration(groupContainer: .identifier("group.org.foo.appname"))
modelContainer = try ModelContainer(for: ClassA.self, ClassB.self, configurations: config)