Skip to content

Commit e1aa5c5

Browse files
committed
Old cache directory keep in disk when new URLCache object assigned
1 parent 7a93011 commit e1aa5c5

File tree

2 files changed

+47
-36
lines changed

2 files changed

+47
-36
lines changed

Foundation/URLCache.swift

+41-31
Original file line numberDiff line numberDiff line change
@@ -151,12 +151,14 @@ open class URLCache : NSObject {
151151
if let cache = sharedCache {
152152
return cache
153153
} else {
154+
guard var cacheDirectoryUrl = FileManager.default.urls(for: .cachesDirectory, in: .userDomainMask).first else {
155+
fatalError("Unable to find cache directory")
156+
}
157+
154158
let fourMegaByte = 4 * 1024 * 1024
155159
let twentyMegaByte = 20 * 1024 * 1024
156-
let bundleIdentifier = Bundle.main.bundleIdentifier ?? UUID().uuidString
157-
let cacheDirectoryPath = FileManager.default.urls(for: .cachesDirectory, in: .userDomainMask).first?.path ?? "\(NSHomeDirectory())/Library/Caches"
158-
let diskPath = cacheDirectoryPath + "/" + bundleIdentifier
159-
let cache = URLCache(memoryCapacity: fourMegaByte, diskCapacity: twentyMegaByte, diskPath: diskPath)
160+
cacheDirectoryUrl.appendPathComponent(ProcessInfo.processInfo.processName)
161+
let cache = URLCache(memoryCapacity: fourMegaByte, diskCapacity: twentyMegaByte, diskPath: cacheDirectoryUrl.path)
160162
sharedCache = cache
161163
cache.persistence?.setupCacheDirectory()
162164
return cache
@@ -167,8 +169,6 @@ open class URLCache : NSObject {
167169
guard newValue !== sharedCache else { return }
168170

169171
sharedSyncQ.sync {
170-
// Remove previous data before resetting new URLCache instance
171-
URLCache.sharedCache?.persistence?.deleteAllCaches()
172172
sharedCache = newValue
173173
newValue.persistence?.setupCacheDirectory()
174174
}
@@ -195,7 +195,7 @@ open class URLCache : NSObject {
195195
self.memoryCapacity = memoryCapacity
196196
self.diskCapacity = diskCapacity
197197

198-
if let _path = path {
198+
if diskCapacity > 0, let _path = path {
199199
self.persistence = _CachePersistence(path: _path)
200200
}
201201

@@ -284,7 +284,7 @@ open class URLCache : NSObject {
284284
@result the current usage of the on-disk cache of the receiver.
285285
*/
286286
open var currentDiskUsage: Int {
287-
return self.syncQ.sync { self.persistence?.cacheSizeInDesk ?? 0 }
287+
return self.syncQ.sync { self.persistence?.cacheSizeInDisk ?? 0 }
288288
}
289289

290290
}
@@ -299,7 +299,9 @@ fileprivate struct _CachePersistence {
299299

300300
let path: String
301301

302-
var cacheSizeInDesk: Int {
302+
// FIXME: Create a stored property
303+
// Update this value as the cache added and evicted
304+
var cacheSizeInDisk: Int {
303305
do {
304306
let subFiles = try FileManager.default.subpathsOfDirectory(atPath: path)
305307
var total: Int = 0
@@ -315,10 +317,6 @@ fileprivate struct _CachePersistence {
315317

316318
func setupCacheDirectory() {
317319
do {
318-
if FileManager.default.fileExists(atPath: path) {
319-
try FileManager.default.removeItem(atPath: path)
320-
}
321-
322320
try FileManager.default.createDirectory(atPath: path, withIntermediateDirectories: true)
323321
} catch {
324322
fatalError("Unable to create directories for URLCache: \(error.localizedDescription)")
@@ -328,15 +326,21 @@ fileprivate struct _CachePersistence {
328326
func saveCachedResponse(_ response: CachedURLResponse, for request: URLRequest) {
329327
let archivedData = NSKeyedArchiver.archivedData(withRootObject: response)
330328
do {
331-
let cacheFileURL = urlForFileIdentifier(request.cacheFileIdentifier)
332-
try archivedData.write(to: cacheFileURL)
329+
if let fileIdentifier = request.cacheFileIdentifier {
330+
let cacheFileURL = urlForFileIdentifier(fileIdentifier)
331+
try archivedData.write(to: cacheFileURL)
332+
}
333333
} catch {
334334
fatalError("Unable to save cache data: \(error.localizedDescription)")
335335
}
336336
}
337337

338338
func cachedResponse(for request: URLRequest) -> CachedURLResponse? {
339-
let url = urlForFileIdentifier(request.cacheFileIdentifier)
339+
guard let fileIdentifier = request.cacheFileIdentifier else {
340+
return nil
341+
}
342+
343+
let url = urlForFileIdentifier(fileIdentifier)
340344
guard let data = try? Data(contentsOf: url),
341345
let response = NSKeyedUnarchiver.unarchiveObject(with: data) as? CachedURLResponse else {
342346
return nil
@@ -345,29 +349,35 @@ fileprivate struct _CachePersistence {
345349
return response
346350
}
347351

348-
func deleteAllCaches() {
349-
do {
350-
try FileManager.default.removeItem(atPath: path)
351-
} catch {
352-
fatalError("Unable to flush database for URLCache: \(error.localizedDescription)")
353-
}
354-
}
355-
356352
private func urlForFileIdentifier(_ identifier: String) -> URL {
357-
return URL(fileURLWithPath: path + "/" + identifier)
353+
return URL(fileURLWithPath: path).appendingPathComponent(identifier)
358354
}
359355

360356
}
361357

362-
fileprivate extension URLRequest {
358+
extension URLRequest {
359+
360+
fileprivate var cacheFileIdentifier: String? {
361+
guard let scheme = self.url?.scheme, scheme == "http" || scheme == "https",
362+
let method = httpMethod, !method.isEmpty,
363+
let urlString = url?.absoluteString else {
364+
return nil
365+
}
366+
367+
var hashString = "\(scheme)_\(method)_\(urlString)"
368+
if let userAgent = self.allHTTPHeaderFields?["User-Agent"], !userAgent.isEmpty {
369+
hashString.append(contentsOf: "_\(userAgent)")
370+
}
371+
372+
if let acceptLanguage = self.allHTTPHeaderFields?["Accept-Language"], !acceptLanguage.isEmpty {
373+
hashString.append(contentsOf: "_\(acceptLanguage)")
374+
}
363375

364-
var cacheFileIdentifier: String {
365-
guard let urlString = url?.absoluteString else {
366-
fatalError("Unable to create cache identifier for request: \(self)")
376+
if let range = self.allHTTPHeaderFields?["Range"], !range.isEmpty {
377+
hashString.append(contentsOf: "_\(range)")
367378
}
368379

369-
let method = httpMethod ?? "GET"
370-
return urlString + method
380+
return String(format: "%X", hashString.hashValue)
371381
}
372382

373383
}

TestFoundation/TestURLCache.swift

+6-5
Original file line numberDiff line numberDiff line change
@@ -16,11 +16,12 @@ class TestURLCache: XCTestCase {
1616
}
1717

1818
private var cacheDirectoryPath: String {
19-
if let path = FileManager.default.urls(for: .cachesDirectory, in: .userDomainMask).first?.path {
20-
return "\(path)/org.swift.TestFoundation"
21-
} else {
22-
return "\(NSHomeDirectory())/Library/Caches/org.swift.TestFoundation"
19+
guard var cacheDirectoryUrl = FileManager.default.urls(for: .cachesDirectory, in: .userDomainMask).first else {
20+
fatalError("Unable to find cache directory")
2321
}
22+
23+
cacheDirectoryUrl.appendPathComponent(ProcessInfo.processInfo.processName)
24+
return cacheDirectoryUrl.path
2425
}
2526

2627
func test_cacheFileAndDirectorySetup() {
@@ -35,7 +36,7 @@ class TestURLCache: XCTestCase {
3536
let newPath = cacheDirectoryPath + ".test_cacheFileAndDirectorySetup/"
3637
URLCache.shared = URLCache(memoryCapacity: fourMegaByte, diskCapacity: twentyMegaByte, diskPath: newPath)
3738
XCTAssertTrue(FileManager.default.fileExists(atPath: newPath))
38-
XCTAssertFalse(FileManager.default.fileExists(atPath: cacheDirectoryPath))
39+
XCTAssertTrue(FileManager.default.fileExists(atPath: cacheDirectoryPath))
3940
}
4041

4142
}

0 commit comments

Comments
 (0)