The key conceptual difference is that localStorage only supports strings, while IndexedDB supports objects, arrays, and binary data like Uint8Array
. This is critical if you’re dealing with large files (like images or PDFs) since binary data in localStorage requires Base64 encoding, which increases file size and complexity. IndexedDB avoids this by storing binary data directly.
Another big difference is that localStorage is synchronous, whereas IndexedDB is asynchronous, allowing for non-blocking storage operations. When working on the Scanbot Web SDK, we stored large image files using IndexedDB + Web Workers to offload heavy processing to a background thread, keeping the app responsive.
Why have two stores? localStorage is simple and fine for small key-value data (like app settings), but IndexedDB is a full client-side database. It’s meant for larger, structured, and binary data, offering better performance, capacity, and indexing.
If you’re interested in working with binary data in IndexedDB or web workers, check out this guide we wrote: https://scanbot.io/techblog/storage-wars-web-edition/. (Full disclosure: I work at Scanbot SDK, but I think this approach can help others deal with large files in the browser.)