last update
May 23, 2026
license
MITv1.0.0
format
SKILL.md
- Install
// Downloads SKILL.md into ~/.claude/skills/android-room-database/
$ curl -fsSL --create-dirs -o ~/.claude/skills/android-room-database/SKILL.md https://claudeskil.com/skills/android-room-database/SKILL.md - Invoke
// Inside Claude Code, type the skill name as a slash command
> /android-room-database help me ship this - Or copy this from the README
// extracted kotlin block
$ @Dao interface TaskDao { @Query("SELECT * FROM task ORDER BY due_at") fun observeAll(): Flow<List<Task>> @Query("SELECT * FROM task WHERE done = 0")
- name:
- Android Room Database
- slug:
- android-room-database
- version:
- v1.0.0
- license:
- MIT
- author:
- @chiragthummar16
- categories:
- tags:
- #room#android#sqlite#ksp#kotlin
- description:
Room ORM scaffolds: entities, DAOs, migrations, Flow queries, type converters, instrumentation tests.
README.md
Android Room Database
Scaffolds a complete Room persistence layer for Kotlin Android apps: entities, DAOs, the database class, type converters, schema-versioned migrations, and the instrumentation tests teams usually leave out. Built around KSP (not kapt) and reactive Flow queries, it targets developers who want a production-shaped data layer instead of a half-wired @Entity and a single getAll().
When to use it
- Standing up the storage layer for a new feature module and you want DAOs, converters, and a
RoomDatabasesubclass wired together correctly the first time. - Adding a column or table and you need a real
Migrationplus aMigrationTestHelpertest so the upgrade doesn't crash on existing installs. - Wiring Paging 3 into a list screen via
PagingSourcefrom a DAO query. - Replacing
LiveDataplumbing withFlow-returning queries that emit on every relevant write.
What it does
It generates @Entity classes (with @PrimaryKey, @ColumnInfo, @Index, @ForeignKey), @Dao interfaces using @Query/@Insert(onConflict = …)/@Update/@Upsert/@Delete, and a @Database class listing entities and version. Reactive reads return Flow<List<T>> or, for paging, PagingSource<Int, T>. @TypeConverter classes handle Instant, enums, and JSON-backed fields.
For migrations it emits both styles: explicit Migration(n, n+1) objects with db.execSQL(...), and @Database(autoMigrations = [AutoMigration(from, to)]) with @RenameColumn/@DeleteColumn specs where a column rename can't be auto-detected. It enables exportSchema = true and points KSP at a schemas/ directory so each version's JSON is committed.
The test harness is the differentiator: a MigrationTestHelper instrumentation test that creates the DB at an old version, inserts rows, runs the migration, and asserts the data survived — plus in-memory Room.inMemoryDatabaseBuilder tests for DAO behavior.
Usage
curl -fsSL --create-dirs -o ~/.claude/skills/android-room-database/SKILL.md https://claudeskil.com/skills/android-room-database/SKILL.md
@Dao
interface TaskDao {
@Query("SELECT * FROM task ORDER BY due_at")
fun observeAll(): Flow<List<Task>>
@Query("SELECT * FROM task WHERE done = 0")
fun pendingPaged(): PagingSource<Int, Task>
@Upsert suspend fun upsert(task: Task)
}
// build.gradle.kts
ksp { arg("room.schemaLocation", "$projectDir/schemas") }
Tips & gotchas
- Use KSP, not kapt — Room's kapt processor is effectively deprecated and slower. The skill assumes
com.google.devtools.kspis applied. - Commit the exported
schemas/*.json.MigrationTestHelperreads them, and without themroom.schemaLocationwarnings become migration-test failures. - Auto-migrations can't infer a column rename or a non-null column with no default — supply an
AutoMigrationSpecor fall back to a manualMigration. - A
Flowquery re-emits on any write to a table it touches, including unrelated rows. Scope queries and usedistinctUntilChanged()to avoid redundant recompositions.
FAQ
Auto-migrations or manual migrations? Auto for additive changes (new table, new nullable column). Manual for renames, type changes, or data backfills. The skill generates the matching test either way.
Does it support KMP? It targets Android Room. Room's multiplatform artifacts exist but the generated instrumentation tests assume an Android test runner.
Why do my migration tests fail with "no such file"? The schemas/ JSON for the starting version isn't on disk — re-run a build at that version or commit the exported schema.
$ cat reviews/