External SPI NOR Flash for ESP32 and Arduino: W25Q Chips, LittleFS, and When Internal Storage Isn't Enough
An ESP32's built-in flash already runs your firmware and can host a LittleFS or SPIFFS partition for config files and small logs, and most projects never need more. But once you're logging sensor data for months, storing a library of pre-rendered assets, buffering audio, or working with a plain Arduino Uno or Nano that has no meaningful onboard flash to spare at all, a dedicated external SPI NOR flash chip is one of the cheapest, most reliable ways to add serious storage without reaching for an SD card and its filesystem-corruption headaches.
What a W25Q chip actually is
The Winbond W25Q series (W25Q32, W25Q64, W25Q128, and so on — the number is roughly the capacity in megabits, so a W25Q128 is 16 MB) are cheap, widely-cloned SPI NOR flash chips originally designed as the boot flash for routers, and now a maker-project staple sold on tiny breakout boards for a couple of dollars. They speak standard SPI, need only four signal lines plus power, and are the same basic chip already soldered onto your ESP32 dev board for firmware storage — you're just adding a second one dedicated to data rather than sharing the one running your code.
NOR flash has a specific personality worth understanding before you build around it: reads are fast and random-access like RAM, but writes require the target region to be erased first, and erasing happens in fixed blocks (typically 4 KB sectors, sometimes larger 32/64 KB blocks) rather than byte by byte. You can't simply overwrite a single byte in place — you erase the whole sector and rewrite it. This is exactly why a real filesystem layer matters instead of hand-rolling your own storage scheme.
Wiring
W25Q PinFunctionESP32 Connection CSChip selectAny GPIO (active low) CLKSPI clockSPI SCK (or any GPIO in software SPI) DO/DI (or SO/SI)SPI dataSPI MISO / MOSI WPWrite protectTie to 3.3V to disable HOLDPause transferTie to 3.3V to disable VCC / GNDPower3.3V — do not run at 5VThese chips are 3.3V parts. Most breakout boards sold for hobbyists include a small regulator and level shifter so they tolerate 5V Arduino logic, but bare chips do not — check the breakout board's silkscreen or datasheet before wiring a 5V Uno directly to a bare W25Q. On an ESP32 there's no ambiguity: everything is already 3.3V, and you can wire the chip straight to the hardware SPI pins (or any GPIOs if you're running the bus in software mode alongside other SPI peripherals).
Software: LittleFS is the right default
Don't write raw sector-erase logic yourself unless you have a specific reason to. LittleFS was designed from the ground up for exactly this kind of NOR/NAND flash with wear-leveling and power-loss resilience built in, and it's well supported for external SPI flash through libraries like Adafruit's Adafruit_SPIFlash combined with Adafruit_LittleFS, or ESP-IDF's native esp_littlefs component pointed at an external flash driver. The workflow looks like this: initialize the SPI flash driver against the chip's JEDEC ID (the library auto-detects most W25Q variants), mount a LittleFS filesystem on top of it, and then use ordinary File/open()/write() calls exactly as you would with the internal filesystem — the wear-leveling and bad-sector handling happen transparently underneath.
This is the meaningful difference from the internal-flash LittleFS setup covered in this site's ESP32 web control panel guide: that project uses a filesystem partition carved out of the same flash chip running your code, which is fine for config files and small web assets, but competes with your firmware image for space and wears the same flash your bootloader depends on. A dedicated external chip keeps heavy write cycles — data logging, circular buffers, anything that rewrites the same region repeatedly — off the flash your firmware boots from.
Picking a capacity and a use case
- Data logging: a W25Q32 (4 MB) holds an enormous number of sensor readings as compact binary records — millions of timestamped float pairs — making it a legitimate low-power alternative to an SD card for a battery-powered logger that just needs to survive between infrequent downloads.
- Asset storage: pre-rendered UI graphics, fonts, or audio clips for a project driving a TFT or speaker, where you want them off the code partition and swappable without reflashing firmware.
- Circular buffers: black-box style logging (last N minutes of telemetry before a fault) benefits from NOR's fast, addressable reads even though writes are block-oriented.
- Bare Arduino boards: an Uno or Nano with no meaningful onboard storage gains a real filesystem it otherwise has no path to.
Endurance and what to watch for
W25Q flash is typically rated for around 100,000 erase cycles per sector, which sounds limiting until you remember that's per sector, not per chip, and LittleFS actively spreads writes across free sectors rather than hammering the same one. A logger writing a record every few seconds will still take years to wear out a modern chip in practice. The real failure mode to design around is power loss mid-write — LittleFS's journaling handles this gracefully for the filesystem structure itself, but always flush/close files after a logical write rather than leaving them open indefinitely if the device might lose power unexpectedly.
External SPI flash sits in a useful gap between the tiny partition you can spare on internal flash and the complexity — and higher current draw — of an SD card. For a battery project already budgeting deep sleep and careful power design, a $2 flash chip that draws microamps in standby and needs no filesystem-corruption recovery plan is often the better call.
Related Guides
- Building a Standalone ESP32 Web Control Panel: AsyncWebServer, LittleFS, and Captive Portal Setup
- How to Program Addressable LED Strips: WS2812B Patterns, Effects, and Power Design
- I2C vs SPI vs UART: How to Choose and Use Serial Communication Protocols
- How to Use Sensors with Arduino and ESP32: Temperature, Distance, Load, Current, and Hall Effect
- How to Control Motors with Arduino and ESP32: Stepper, DC, and Servo Drivers
- ESP32: Setting Up for Arduino IDE
- Arduino vs ESP32: Which Should You Use? A Practical Comparison
- Getting Started with ESP32: GPIO, WiFi, and Your First Project