Skip to content
AB

Room Versus DataStore: Choose Storage by Data Shape

Use DataStore for preferences and Room for relational, queryable, migratable application data.

Ashish BhakhandPublished

Room and DataStore solve different persistence problems.

DataStore fits small configuration values: selected theme, dismissed education, preferred units, or a last-used filter. It exposes transactional updates and a Flow without pretending preferences are tables.

Room fits records that need identity, relationships, indexes, queries, and migrations: workouts, health snapshots, scores, and sync tombstones.

Code
@Entity(indices = [Index(value = ["userId", "day"], unique = true)])
data class DailyVitalsEntity(
    @PrimaryKey val id: String,
    val userId: String,
    val day: LocalDate,
    val steps: Long?,
    val updatedAt: Instant,
)

Room verifies SQL at build time and can expose reactive queries. It also requires migration discipline and careful threading for transactions.

Do not serialize an ever-growing list of records into DataStore. Updating one item rewrites the value, queries require loading everything, and schema evolution becomes manual.

Likewise, creating a database table for one theme enum adds unnecessary machinery.

The decision comes from access patterns: key-value configuration versus structured data with independent lifecycles. Choosing by data shape keeps both tools simple.

← Back to all writing