Your app makes an API call, gets back a response full of the user's data, and shows it. Behind the scenes, iOS may have quietly written that response to a cache file on disk, in plaintext, so it can serve it faster next time. NSURLCache, part of the URL loading system, does this automatically, which is great for performance and a problem if the responses contain sensitive data. A cached response holding personal information or anything confidential becomes data at rest you did not intend to store, recoverable on a compromised device or from a backup. Here is what NSURLCache does, where the leak happens, and how to keep sensitive responses out of the cache.
Short answer
NSURLCache is the iOS URL loading system's HTTP response cache, which can store responses your app receives in memory and on disk to speed up repeat requests. Per Apple, this caching is automatic, so if a response contains sensitive data, it can be written to a cache file on disk in plaintext, where it persists and can be recovered on a compromised device or swept into a backup. The fix is to keep sensitive responses out of the cache: use an ephemeral session configuration or disable caching for sensitive requests, have the server send no-store cache directives, and clear the cache on logout. Treat cached responses as part of your data-at-rest surface, and do not let sensitive API data be cached on disk.
What you should know
NSURLCachecaches HTTP responses: in memory and on disk, automatically.- Cached responses can hold sensitive data: written to disk in plaintext.
- It persists and can leak: recoverable on a compromised device or backup.
- Disable caching for sensitive requests: ephemeral sessions or per-request policy.
- Clear the cache on logout: and have the server send no-store.
What is NSURLCache, and what is the risk?
It is the cache behind the URL loading system, storing responses so repeated requests can be served without hitting the network. When your app makes HTTP requests through the standard networking APIs, the system can cache the responses according to cache policy and the response's headers, keeping them in memory and writing them to a cache store on disk in the app's container. For performance this is helpful, a repeated request can be answered from the cache. The risk is that this happens automatically and indiscriminately unless you control it, so a response carrying sensitive data, an API result with personal information, account details, or other confidential content, can be written to the on-disk cache in plaintext. That cached copy persists beyond the moment it was shown, joining your app's data-at-rest footprint, where it could be read on a jailbroken or compromised device or included in a device backup. So the issue is not that caching exists, but that sensitive responses get cached by default when you have not told the system otherwise.
Where does sensitive data leak?
Into the cache store and anywhere it travels. The table lists the paths.
| Path | Exposure |
|---|---|
| On-disk cache store | Sensitive responses written to disk in plaintext |
| Persistence | The cached copy outlives its display |
| Device backups | The cache included in a backup |
| Compromised device | Cache files read on a jailbroken device |
| WKWebView cache | Web content cached separately by a web view |
The primary leak is the on-disk cache store: responses written there sit in plaintext in the app's container, so any sensitive content in a cached API response is now stored, and it persists past the moment it was needed, which is the essence of an unintended data-at-rest exposure. From there it can travel: the cache can be included in device backups, and on a compromised or jailbroken device the cache files can be read directly. If your app shows web content, a WKWebView maintains its own cache as well, a separate store with the same kind of concern. In every case the underlying problem is the same, sensitive data persisted on the device through caching you did not intend, so the response that was meant to be transient is actually retained.
How do you prevent caching sensitive responses?
Tell the system not to cache them, on both the client and the server. On the client, for requests that return sensitive data, avoid the default caching: use an ephemeral session configuration, which keeps no persistent cache on disk, for sensitive traffic, or disable the cache for those requests by setting an appropriate cache policy or removing the cache from the session configuration. On the server, send cache-control directives such as no-store on responses with sensitive content, so the system does not cache them regardless of client defaults, which is a clean, declarative control. Clear the cache when it matters, calling the cache's remove-all on logout so a previous user's cached responses do not linger for the next person or on the device. If you use a WKWebView for sensitive content, manage its data store too, since it caches separately. The principle is to decide which responses are sensitive and ensure those are never written to disk, through ephemeral or non-caching sessions and no-store directives, while letting ordinary, non-sensitive responses cache for performance. Match caching to sensitivity, rather than letting everything cache by default.
What to watch out for
The first trap is relying on default caching for sensitive API responses, which writes them to disk in plaintext where they persist; use ephemeral or non-caching sessions and no-store for sensitive requests. The second is forgetting the cache is included in backups and readable on a compromised device. The third is overlooking the separate WKWebView cache and not clearing cached responses on logout. Caching behavior is configured in your networking and on your server, so a pre-submission scan such as PTKD.com (https://ptkd.com), which reads the compiled IPA against OWASP MASVS, assesses your app's data-at-rest posture, the storage surface the response cache belongs to, while the cache configuration is yours to set.
What to take away
NSURLCacheautomatically caches HTTP responses in memory and on disk, so sensitive responses can be written to disk in plaintext and persist as unintended data at rest.- The cached data can be read on a compromised device, included in backups, and a
WKWebViewcaches separately, all extending the exposure. - Prevent it by using ephemeral or non-caching sessions for sensitive requests, sending no-store directives from the server, and clearing the cache on logout.
- Treat cached responses as part of your data-at-rest surface, and use a pre-submission scan such as PTKD.com to assess your storage posture.



