Added hash-code to in-memory database names.
Useful for determining which in-memory database is being inspected.
Previously they were all called ":memory:".
Bug: 154485527
Bug: 143216096
Test: ./gradlew :sqlite:sqlite-inspection:cC
Change-Id: I0065916bece4dad14032017b648c84ca920fcbb8
diff --git a/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/DatabaseExtensions.kt b/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/DatabaseExtensions.kt
index a21ea10..6c536f0 100644
--- a/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/DatabaseExtensions.kt
+++ b/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/DatabaseExtensions.kt
@@ -25,6 +25,10 @@
fun SQLiteDatabase.addTable(table: Table) = execSQL(table.toCreateString())
+val SQLiteDatabase.displayName: String
+ get() = if (path != ":memory:") path else
+ ":memory: {hashcode=0x${String.format("%x", this.hashCode())}}"
+
fun SQLiteDatabase.insertValues(table: Table, vararg values: String) {
assertThat(values).isNotEmpty()
assertThat(values).hasLength(table.columns.size)
diff --git a/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/QueryTest.kt b/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/QueryTest.kt
index 4c9f6c9..fe8be48 100644
--- a/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/QueryTest.kt
+++ b/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/QueryTest.kt
@@ -542,7 +542,7 @@
)
)
testEnvironment.sendCommand(createTrackDatabasesCommand())
- return testEnvironment.awaitDatabaseOpenedEvent(databaseInstance.path).databaseId
+ return testEnvironment.awaitDatabaseOpenedEvent(databaseInstance.displayName).databaseId
}
private suspend fun issueQuery(
diff --git a/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/SqliteInspectorTestEnvironment.kt b/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/SqliteInspectorTestEnvironment.kt
index f53f32f..f3ba436 100644
--- a/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/SqliteInspectorTestEnvironment.kt
+++ b/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/SqliteInspectorTestEnvironment.kt
@@ -109,7 +109,7 @@
): Int {
registerAlreadyOpenDatabases(listOf(databaseInstance))
sendCommand(MessageFactory.createTrackDatabasesCommand())
- return awaitDatabaseOpenedEvent(databaseInstance.path).databaseId
+ return awaitDatabaseOpenedEvent(databaseInstance.displayName).databaseId
}
/**
diff --git a/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/TrackDatabasesTest.kt b/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/TrackDatabasesTest.kt
index 77ec1e2..218323a 100644
--- a/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/TrackDatabasesTest.kt
+++ b/sqlite/sqlite-inspection/src/androidTest/java/androidx/sqlite/inspection/test/TrackDatabasesTest.kt
@@ -72,7 +72,7 @@
testEnvironment.assertNoQueuedEvents()
assertThat(actual.map { it.databaseId }.distinct()).hasSize(expected.size)
expected.forEachIndexed { ix, _ ->
- assertThat(actual[ix].path).isEqualTo(expected[ix].path)
+ assertThat(actual[ix].path).isEqualTo(expected[ix].displayName)
}
}
@@ -95,7 +95,7 @@
val database = Database("db3_$ix").createInstance(temporaryFolder)
assertThat(exitHook.onExit(database)).isSameInstanceAs(database)
testEnvironment.receiveEvent().let { event ->
- assertThat(event.databaseOpened.path).isEqualTo(database.path)
+ assertThat(event.databaseOpened.path).isEqualTo(database.displayName)
}
}
@@ -117,7 +117,7 @@
assertThat(event.hasDatabaseOpened()).isEqualTo(true)
val isNewId = seenDbIds.add(event.databaseOpened.databaseId)
assertThat(isNewId).isEqualTo(true)
- assertThat(event.databaseOpened.path).isEqualTo(database.path)
+ assertThat(event.databaseOpened.path).isEqualTo(database.displayName)
}
// file based db: first open
diff --git a/sqlite/sqlite-inspection/src/main/java/androidx/sqlite/inspection/SqliteInspector.java b/sqlite/sqlite-inspection/src/main/java/androidx/sqlite/inspection/SqliteInspector.java
index e214fd8..0d6e753c 100644
--- a/sqlite/sqlite-inspection/src/main/java/androidx/sqlite/inspection/SqliteInspector.java
+++ b/sqlite/sqlite-inspection/src/main/java/androidx/sqlite/inspection/SqliteInspector.java
@@ -98,6 +98,12 @@
"executeInsert()J",
"executeUpdateDelete()I");
+ private static final String sInMemoryDatabasePath = ":memory:";
+
+ /** Placeholder {@code %x} is for database's hashcode */
+ private static final String sInMemoryDatabaseNameFormat =
+ sInMemoryDatabasePath + " {hashcode=0x%x}";
+
private static final int INVALIDATION_MIN_INTERVAL_MS = 1000;
// Note: this only works on API26+ because of pragma_* functions
@@ -532,12 +538,21 @@
// TODO: replace with db open/closed tracking as this will keep the database open
database.acquireReference();
- String path = database.getPath();
- response = createDatabaseOpenedEvent(id, path);
+ response = createDatabaseOpenedEvent(id, generateDatabaseName(database));
mRoomInvalidationRegistry.invalidateCache();
getConnection().sendEvent(response.toByteArray());
}
+ private static String generateDatabaseName(@NonNull SQLiteDatabase database) {
+ return isInMemoryDatabase(database)
+ ? String.format(sInMemoryDatabaseNameFormat, database.hashCode())
+ : database.getPath();
+ }
+
+ private static boolean isInMemoryDatabase(@NonNull SQLiteDatabase database) {
+ return Objects.equals(sInMemoryDatabasePath, database.getPath());
+ }
+
private Event createDatabaseOpenedEvent(int id, String path) {
return Event.newBuilder().setDatabaseOpened(
DatabaseOpenedEvent.newBuilder()
@@ -601,7 +616,6 @@
}
static class DatabaseRegistry {
- private static final String IN_MEMORY_DB_PATH = ":memory:";
static final int ALREADY_TRACKED = -1;
private final Object mLock = new Object();
@@ -629,9 +643,8 @@
return ALREADY_TRACKED;
}
// Path already tracked (and not an in-memory database)
- final String path = database.getPath();
- if (!Objects.equals(IN_MEMORY_DB_PATH, path)
- && Objects.equals(path, entry.getValue().getPath())) {
+ if (!isInMemoryDatabase(database)
+ && Objects.equals(database.getPath(), entry.getValue().getPath())) {
return ALREADY_TRACKED;
}
}