Background
Sections
IntroductionRequirements & Problem AnalysisConstraints & AssumptionsEstimation TechniquesFunctional vs Non-Functional RequirementsMoSCoW PrioritizationSystem Design FundamentalsArchitecture DiagramClass DiagramComponent DiagramData Flow Diagram (DFD)ER Diagram (Entity-Relationship Diagram)High Level Design (HLD)Low Level Design (LLD)Sequence DiagramState DiagramUse Case DiagramData StorageDocument StoresFile StorageGraph DatabasesIn-Memory DatabasesKey-Value StoresNewSQLNoSQL DatabasesObject StorageSQL Databases (RDBMS)Time-Series DatabasesWide-Column StoresDatabase ConceptsACID PropertiesCAP TheoremConsistency ModelsIndexingNormalization & DenormalizationReplicationSharding & PartitioningTransactions & Isolation LevelsScalabilityAuto-Scaling & ElasticityConsensus & Leader ElectionLoad BalancingReplication & Read ReplicasSharding & PartitioningVertical vs Horizontal ScalingAvailability & ReliabilityBackup & Data DurabilityCircuit BreakerData ConsistencyDisaster RecoveryFault Tolerance & FailoverGraceful DegradationHigh AvailabilityNetworkingCDNDNSFirewalls & VPNHTTP & HTTPSLoad Balancer & Reverse ProxyTCP/IP & UDPWebSocketsCachingCache InvalidationCache Read/Write PatternsCaching LayersEviction PoliciesRedis vs MemcachedMessaging & CommunicationDead-Letter QueueIdempotencyKafka vs RabbitMQ vs SQSMessage QueuesPub/SubCompute & ServicesAPI GatewayContainers & OrchestrationMonolith vs MicroservicesServerlessService DiscoveryService MeshWeb Server & App ServerAPI DesignAPI Versioning & IdempotencyAuthentication & AuthorizationGraphQLgRPCPaginationRate Limiting & ThrottlingRESTSecurityAuthentication & AuthorizationData PrivacyEncryptionInput Validation & InjectionOAuth2 & JWTSecrets ManagementXSS & CSRFStorage & File SystemsBackup & RetentionBlock vs File vs Object StorageData Lakes & WarehousesDistributed File SystemsEphemeral StorageObservability & MonitoringDistributed TracingHealth ChecksLoggingMetricsSLI, SLO, SLADesign PatternsBulkhead PatternCircuit Breaker PatternCreational PatternsRate Limiter PatternRetry PatternStructural & Behavioral Patterns

Block vs File vs Object Storage

8 min read

In a Nutshell

There are three fundamental ways to store data on disk, and they differ in how data is organized and accessed. Block storage exposes raw, fixed-size chunks (blocks) that the operating system formats and manages — it's what a hard drive or cloud volume looks like, fast and low-level, ideal for databases and boot volumes. File storage organizes data as a hierarchy of files and folders accessible over a shared filesystem, ideal when multiple machines need to share files. Object storage stores data as discrete objects (a blob + metadata + a unique ID) in a flat namespace accessed via HTTP APIs — infinitely scalable and cheap, ideal for images, videos, backups, and static assets. Choosing the right one is a foundational infrastructure decision.

2D minimalistic diagram with three panels: left "Block" shows raw fixed-size blocks that a server formats into a filesystem (attached like a disk); middle "File" shows a hierarchical folder/file tree shared by multiple servers over a network mount; right "Object" shows a flat pool of objects each with a key, metadata, and blob, accessed via HTTP GET/PUT

How It Actually Works

The Three Models Compared

Block Storage File Storage Object Storage
Unit Fixed-size blocks Files in a hierarchy Objects (blob + metadata + ID)
Access Attached as a disk (low-level) Filesystem protocol (NFS/SMB) HTTP API (GET/PUT/DELETE)
Namespace Raw blocks (OS imposes structure) Hierarchical (folders) Flat (key → object)
Metadata Minimal Filesystem attributes Rich, custom metadata
Scalability Limited (volume size) Moderate Virtually unlimited
Performance Highest, lowest latency Good Higher latency (HTTP)
Shared access Usually one host Many hosts Any client, anywhere
Cost Higher Moderate Lowest
Examples AWS EBS, iSCSI NFS, AWS EFS, SMB AWS S3, GCS, Azure Blob
Best for Databases, boot disks, low-latency Shared files, legacy apps Media, backups, static assets, data lakes

Block Storage: Raw and Fast

Block storage presents raw volumes that the OS formats with a filesystem (ext4, NTFS) and manages directly. Because there's no abstraction layer between the app and the blocks, it's the fastest, lowest-latency option — which is why databases (which need fast random reads/writes) and boot volumes run on block storage.

Database server → attached block volume (EBS)
  → OS formats it (ext4) → DB writes at the block level → fast random I/O
  Typically attached to ONE host at a time (like a physical disk).

File Storage: Shared Hierarchy

File storage exposes a traditional folder/file hierarchy over a network protocol (NFS, SMB), so multiple machines can mount and share the same filesystem. It's the natural fit for shared documents, home directories, and legacy applications that expect a POSIX filesystem.

Server A ─┐
Server B ─┼─ mount → /shared/filesystem  (NFS/EFS)
Server C ─┘   all read/write the same files, see the same hierarchy

Object Storage: Flat, Scalable, HTTP

Object storage stores each item as an object — the data blob plus rich metadata plus a unique key — in a flat namespace (no real folders; "paths" are just key prefixes). You access it over HTTP, not a filesystem. There's no in-place editing: you replace whole objects. This design trades low-level performance and POSIX semantics for near-infinite scalability, durability (11 nines), and low cost (see Object Storage).

PUT  /my-bucket/images/photo.jpg   (upload an object)
GET  /my-bucket/images/photo.jpg   (retrieve it)
  - flat namespace: "images/" is just a key prefix, not a folder
  - rich metadata, versioning, lifecycle tiers, HTTP access from anywhere
  - immutable objects: to "edit," you overwrite the whole object

Choosing the Right Storage

Need a disk for a database or OS?                → BLOCK  (fast, low-latency)
Need many servers to share files (POSIX)?        → FILE   (shared hierarchy)
Storing media, backups, static assets, at scale? → OBJECT (cheap, unlimited)

The most common modern default for application data (user uploads, images, documents, backups) is object storage — it's cheap, effectively unlimited, durable, and accessible over HTTP/CDN. Block storage is reserved for what genuinely needs low-latency block access (databases); file storage for shared-filesystem workloads.

2D minimalistic decision-tree diagram: start "What are you storing?" branching to three outcomes — "Database / OS disk (low-latency)" to Block storage; "Files shared by many servers" to File storage; "Media / backups / static assets at scale" to Object storage — each with a representative icon

Seeing It in Action

Scenario: Choosing storage for each part of a photo-sharing application.

User-uploaded photos + videos:
  → OBJECT storage (S3).
    Millions of files, any size, accessed over HTTP, served via CDN.
    11-nines durability, cheap, effectively unlimited, lifecycle tiering
    (move old photos to cheaper cold storage automatically).
    Immutability is fine — a photo is written once, read many times.

The application's PostgreSQL database (users, metadata, likes):
  → BLOCK storage (EBS).
    The DB needs fast, low-latency random reads/writes — exactly block
    storage's strength. Attached to the DB instance like a physical disk.
    Photo BLOBS are NOT stored here — only their metadata + S3 keys.

Shared config / ML training data mounted by many worker nodes:
  → FILE storage (EFS/NFS).
    A fleet of processing workers all mount the same filesystem to read
    shared model files and write intermediate results with POSIX semantics.

The anti-pattern to avoid:
  ✗ Storing photos as BLOBs in the PostgreSQL database.
    → bloats the DB, slows backups, wastes expensive block storage,
      and can't be served directly via CDN. Store the FILE in object
      storage; store only the URL/key + metadata in the database.

Why matching storage to workload matters: each storage type is optimized for a different access pattern, and using the wrong one is expensive in performance, cost, or both. The photo-sharing app uses all three deliberately: object storage for the bulk media (cheap, unlimited, CDN-friendly, durable), block storage for the database that needs genuine low-latency I/O, and file storage where many nodes must share a POSIX filesystem. The classic mistake — cramming large binary files into a relational database on block storage — combines the worst of both: it wastes the expensive, fast block storage on data that doesn't need speed, bloats the database and its backups, and forfeits the CDN-delivery and lifecycle-tiering that object storage gives for free. The right pattern separates the file (object storage) from its metadata and relationships (database), letting each storage type do what it's built for.

Interview Questions

  1. Q: What are the three storage types and how do they differ fundamentally? Hint: Block (raw fixed-size blocks attached as a disk; the OS imposes a filesystem; fastest/lowest-latency; databases, boot volumes). File (hierarchical files/folders shared over NFS/SMB; many hosts share one POSIX filesystem). Object (discrete objects = blob + metadata + key in a flat namespace, accessed via HTTP; near-infinite scale, cheap, durable; media/backups/static assets). They differ in access model, namespace, scalability, and performance.

  2. Q: Why is block storage used for databases? Hint: Databases need fast, low-latency random reads and writes, and block storage provides raw block-level access with no abstraction layer between the app and the disk — the lowest-latency option. The OS formats it with a filesystem the DB controls. File and object storage add layers (network filesystem protocols, HTTP APIs) that introduce latency unsuitable for a database's I/O patterns.

  3. Q: What makes object storage so scalable and cheap, and what does it give up? Hint: A flat namespace (key → object) with no filesystem hierarchy to maintain, HTTP access, and immutable whole-object writes let it scale horizontally to near-infinite capacity across commodity hardware with high durability (11 nines) at low cost. It gives up low-latency block access, POSIX semantics, and in-place editing (you overwrite whole objects) — so it's wrong for databases or workloads needing random writes.

  4. Q: When would you choose file storage over object storage? Hint: When multiple machines need to share a POSIX filesystem with a folder hierarchy and standard file operations — shared documents, home directories, legacy apps expecting a mounted filesystem, or a worker fleet reading/writing shared files with filesystem semantics. Object storage can't be mounted as a POSIX filesystem or edited in place, so file storage fits shared-filesystem workloads that object storage can't serve.

  5. Q: Why is storing large files as BLOBs in a relational database an anti-pattern? Hint: It bloats the database, slows backups/restores and replication, consumes expensive low-latency block storage for data that doesn't need speed, and can't be served directly via CDN. The better pattern stores the file in object storage (cheap, durable, CDN-friendly, lifecycle-tiered) and keeps only the object key/URL plus metadata in the database — separating the bulk file from its relationships.

References

Dive Deeper