SwiftUI Widget更新滞后一步的问题排查求助
SwiftUI Widget更新滞后一步的问题排查求助
背景
我在SwiftUI项目中做了一个公交查询小组件:主应用支持用户查看所有公交站的时刻表,还能把常用站点的公交标记为「收藏」,这些收藏数据用SwiftData存在本地。小组件的核心功能就是展示用户收藏的前4条公交的实时到站信息。
为了让小组件同步主应用的收藏更新,我在主应用里每次执行context.insert或者context.delete操作后,都会立刻调用WidgetCenter.shared.reloadAllTimelines(),想着这样就能触发小组件刷新最新数据。
小组件的Timeline Provider里,我用异步Task来获取数据并生成时间线,核心代码如下:
@MainActor func getTimeline(in context: Context, completion: @escaping (Timeline<Entry>) -> ()) { Task{ // 1. 从Core Data获取收藏数据 let faveServicesSaved = getFavourites() print("Widget: Get Favourites Triggered \(faveServicesSaved.count)") // 获取实时到站信息 let faveServicesReturned = try? await fetchAllData(services: faveServicesSaved) print("Widget: Arrival Data Retrieved \(faveServicesReturned?.count)") // 按位置排序 let faveServicesSorted = sortByLocation(faveServicesReturned ?? []) print("Widget: Sorted by location \(faveServicesSorted.count)") // 取前4条用于展示 let nearestFaveServices = faveServicesSorted.prefix(4) print("Widget: Nearest fave services \(nearestFaveServices.count)") let entry = Favourites(date: Date(), services: Array(nearestFaveServices)) let timeline = Timeline(entries: [entry], policy: .never) completion(timeline) } } // 由于Timeline Provider无法直接使用@Query,通过Core Data手动获取数据 @MainActor private func getFavourites() ->[FaveService]{ guard let container = try? ModelContainer(for: FaveService.self) else { print("Widget: Problem with container setup") return [] } let descriptor = FetchDescriptor<FaveService>() let faves = try? container.mainContext.fetch(descriptor) print("Widget \(faves?.count)") return faves ?? [] }
问题描述
现在遇到了一个很奇怪的问题:小组件的更新总是滞后一步。具体表现为:
- 第一次在主应用添加收藏,小组件完全没显示这条新收藏;
- 当我添加第二条收藏时,小组件才会显示第一条;
- 添加第三条时,显示第二条,以此类推,每次都慢一拍。
已尝试的解决方案
我已经排查了几个方向,但问题还是没解决:
- 确认主应用里
reloadAllTimelines()确实是在context.insert操作完成之后才调用的; - 检查所有涉及数据操作的代码都运行在主线程,避免多线程更新冲突;
- 验证模型容器初始化正常,首次启动时能正确拉取到收藏数据;
- 尝试更换时间线更新策略,包括
.atEnd和.after(Date().addingTimeInterval(60)),但没有任何改善。
有没有大佬能帮忙分析下,这种滞后一步的更新可能是什么原因导致的?
备注:内容来源于stack exchange,提问作者user16405656
相关产品推荐
相关产品推荐

