Files
GIFCollector/GIFCollector MessagesExtension/Services/DownloadService.swift
Joshua Higgins 8ce5adc766 Save GIFs Locally
2025-06-03 22:18:23 -04:00

60 lines
2.0 KiB
Swift

import Foundation
import UIKit
class DownloadService {
static let shared = DownloadService()
private let cache = NSCache<NSString, NSData>()
private var activeTasks: [URL: URLSessionDataTask] = [:]
private init() {
cache.totalCostLimit = 50 * 1024 * 1024 // 50 MB cache limit
}
func downloadGIF(from urlString: String, completion: @escaping (Data?, Error?) -> Void) {
guard let url = URL(string: urlString) else {
completion(nil, NSError(domain: "DownloadService", code: 1, userInfo: [NSLocalizedDescriptionKey: "Invalid URL"]))
return
}
// Check if the GIF is already cached
let cacheKey = url.absoluteString as NSString
if let cachedData = cache.object(forKey: cacheKey) {
completion(cachedData as Data, nil)
return
}
// Cancel any existing tasks for this URL
activeTasks[url]?.cancel()
// Create a new download task
let task = URLSession.shared.dataTask(with: url) { [weak self] data, response, error in
defer {
self?.activeTasks.removeValue(forKey: url)
}
guard let self = self, error == nil, let data = data else {
DispatchQueue.main.async {
completion(nil, error ?? NSError(domain: "DownloadService", code: 2, userInfo: [NSLocalizedDescriptionKey: "Failed to download GIF"]))
}
return
}
// Cache the downloaded data
self.cache.setObject(data as NSData, forKey: cacheKey, cost: data.count)
DispatchQueue.main.async {
completion(data, nil)
}
}
// Store and start the task
activeTasks[url] = task
task.resume()
}
func cancelAllTasks() {
activeTasks.values.forEach { $0.cancel() }
activeTasks.removeAll()
}
}