SwiftUI中TwitchAPI批量请求内存泄漏问题求助
解决方案
1. 修正数据模型的错误定义
你的myFollower结构体中包含了pagination字段,这是错误的——Twitch API返回的分页游标是顶层响应的一部分,并非单个粉丝对象的属性。这个冗余字段会导致每条粉丝数据都占用额外内存,在数据量大时会显著增加内存消耗。修正后的模型如下:
struct myFollower: Codable { let followed_at: String let from_id: String let from_login: String let from_name: String let to_id: String let to_login: String let to_name: String } struct TwitchFollowersResponse: Codable { let data: [myFollower] let total: Int? let pagination: Pagination? } struct Pagination: Codable { let cursor: String? }
2. 分批处理数据,避免内存累积
不要一次性将所有粉丝数据保存在内存数组中,而是每获取一批数据就立刻处理(如写入数据库、本地文件),处理完成后释放该批次的内存。改造后的async/await函数如下:
func fetchFollowersBatchByBatch(token: String, targetUserId: String, limit: Int = GlobalConstants.LOADING_LIMIT, batchHandler: @escaping ([myFollower], Int) async -> Void) async throws { var cursor: String? = nil var totalCount: Int? = nil var processed = 0 repeat { // 构建请求URL,首次请求不带after参数 var endpoint = "https://api.twitch.tv/helix/users/follows?to_id=\(targetUserId)&first=100" if let cursor = cursor { endpoint += "&after=\(cursor)" } var request = URLRequest(url: URL(string: endpoint)!) request.addValue("Bearer \(token)", forHTTPHeaderField: "Authorization") request.addValue(GlobalConstants.CLIENT_ID, forHTTPHeaderField: "Client-ID") let (data, response) = try await URLSession.shared.data(for: request) // 验证响应状态 guard let httpResp = response as? HTTPURLResponse, httpResp.statusCode == 200 else { throw NSError(domain: "TwitchAPI", code: (response as? HTTPURLResponse)?.statusCode ?? -1, userInfo: [NSLocalizedDescriptionKey: "请求失败"]) } // 解析数据 let responseData = try JSONDecoder().decode(TwitchFollowersResponse.self, from: data) let batch = responseData.data.compactMap { $0 } // 记录总数量(仅首次请求获取) if totalCount == nil { totalCount = responseData.total } processed += batch.count // 回调处理当前批次数据,处理后该批次内存会被自动回收 await batchHandler(batch, totalCount ?? processed) // 更新游标 cursor = responseData.pagination?.cursor } while processed < limit && cursor != nil }
3. 严格串行处理多用户请求
确保遍历多个用户时,逐个串行执行粉丝拉取逻辑,避免并发请求导致的内存叠加。示例代码:
func processMultipleUsers(token: String, userIds: [String]) async throws { for userId in userIds { try await fetchFollowersBatchByBatch(token: token, targetUserId: userId) { batch, total in // 在这里处理当前批次数据,比如写入CoreData或本地文件 autoreleasepool { // 包裹处理逻辑,加速临时对象的内存释放 print("处理用户\(userId)的\(batch.count)条粉丝,累计已处理\(total)条") // 执行写入/存储操作... } } } }
4. 优化内存回收
- 在批次数据处理逻辑外包裹
autoreleasepool,强制回收JSON解析、数据转换过程中产生的临时对象。 - 避免在闭包中捕获不必要的强引用,确保没有循环引用导致内存泄漏。
内容的提问来源于stack exchange,提问作者Zeddi
相关产品推荐
相关产品推荐

