视图已配置modelContext,调用Query()却提示需设置该上下文问题咨询
问题:SwiftUI中Query调用报错"Set a .modelContext in view's environment to use Query"
控制台报错:
Set a .modelContext in view's environment to use Query视图环境已配置
modelContext,且能成功向模型容器添加数据,但同一函数内调用Query()时触发上述报错,相关代码如下:let currentTrainPredicate = #Predicate<Train> { train in train.number == currentTrainNumber } // Update the value if it exists if let currentTrain = Query(filter: currentTrainPredicate).wrappedValue.first { currentTrain.dateViewed = Date() } else { self.train.dateViewed = Date() modelContext.insert(self.train) }
解决方法
你错误地直接实例化了Query并访问它的wrappedValue——Query是SwiftUI的属性包装器,只能作为视图的属性声明使用,不能在函数内部直接创建实例调用。
正确的做法有两种:
方法1:使用属性包装器声明Query
在视图结构体中添加@Query属性,让它自动关联环境中的modelContext:
struct YourView: View { @Environment(\.modelContext) private var modelContext let currentTrainNumber: String let train: Train // 声明@Query属性,自动绑定环境中的modelContext @Query(filter: #Predicate<Train> { $0.number == currentTrainNumber }) private var matchingTrains: [Train] var body: some View { Button("Update Train") { updateTrain() } } private func updateTrain() { if let currentTrain = matchingTrains.first { currentTrain.dateViewed = Date() } else { train.dateViewed = Date() modelContext.insert(train) } } }
方法2:直接用modelContext执行查询
如果不需要SwiftUI自动订阅数据更新,可直接通过modelContext的fetch方法完成函数内的临时查询:
private func updateTrain() { let currentTrainPredicate = #Predicate<Train> { train in train.number == currentTrainNumber } let fetchDescriptor = FetchDescriptor<Train>(predicate: currentTrainPredicate) do { let matchingTrains = try modelContext.fetch(fetchDescriptor) if let currentTrain = matchingTrains.first { currentTrain.dateViewed = Date() } else { train.dateViewed = Date() modelContext.insert(train) } } catch { print("查询失败:\(error.localizedDescription)") } }
核心原因:Query(即@Query)依赖SwiftUI的环境系统来自动获取modelContext,它设计用来作为视图的属性,由SwiftUI负责管理数据订阅和视图更新。直接实例化Query时,它无法从环境中获取modelContext,因此触发报错。
内容的提问来源于stack exchange,提问作者José María
相关产品推荐
相关产品推荐

