213 lines
9 KiB
Java
213 lines
9 KiB
Java
package androidx.room;
|
|
|
|
import android.database.Cursor;
|
|
import androidx.annotation.NonNull;
|
|
import androidx.annotation.Nullable;
|
|
import androidx.annotation.RestrictTo;
|
|
import androidx.room.migration.Migration;
|
|
import androidx.sqlite.db.SimpleSQLiteQuery;
|
|
import androidx.sqlite.db.SupportSQLiteDatabase;
|
|
import androidx.sqlite.db.SupportSQLiteOpenHelper;
|
|
import c.d.b.a.a;
|
|
import java.util.List;
|
|
@RestrictTo({RestrictTo.Scope.LIBRARY_GROUP_PREFIX})
|
|
public class RoomOpenHelper extends SupportSQLiteOpenHelper.Callback {
|
|
@Nullable
|
|
private DatabaseConfiguration mConfiguration;
|
|
@NonNull
|
|
private final Delegate mDelegate;
|
|
@NonNull
|
|
private final String mIdentityHash;
|
|
@NonNull
|
|
private final String mLegacyHash;
|
|
|
|
@RestrictTo({RestrictTo.Scope.LIBRARY_GROUP_PREFIX})
|
|
public static abstract class Delegate {
|
|
public final int version;
|
|
|
|
public Delegate(int i) {
|
|
this.version = i;
|
|
}
|
|
|
|
public abstract void createAllTables(SupportSQLiteDatabase supportSQLiteDatabase);
|
|
|
|
public abstract void dropAllTables(SupportSQLiteDatabase supportSQLiteDatabase);
|
|
|
|
public abstract void onCreate(SupportSQLiteDatabase supportSQLiteDatabase);
|
|
|
|
public abstract void onOpen(SupportSQLiteDatabase supportSQLiteDatabase);
|
|
|
|
public void onPostMigrate(SupportSQLiteDatabase supportSQLiteDatabase) {
|
|
}
|
|
|
|
public void onPreMigrate(SupportSQLiteDatabase supportSQLiteDatabase) {
|
|
}
|
|
|
|
@NonNull
|
|
public ValidationResult onValidateSchema(@NonNull SupportSQLiteDatabase supportSQLiteDatabase) {
|
|
validateMigration(supportSQLiteDatabase);
|
|
return new ValidationResult(true, null);
|
|
}
|
|
|
|
@Deprecated
|
|
public void validateMigration(SupportSQLiteDatabase supportSQLiteDatabase) {
|
|
throw new UnsupportedOperationException("validateMigration is deprecated");
|
|
}
|
|
}
|
|
|
|
@RestrictTo({RestrictTo.Scope.LIBRARY_GROUP_PREFIX})
|
|
public static class ValidationResult {
|
|
@Nullable
|
|
public final String expectedFoundMsg;
|
|
public final boolean isValid;
|
|
|
|
public ValidationResult(boolean z2, @Nullable String str) {
|
|
this.isValid = z2;
|
|
this.expectedFoundMsg = str;
|
|
}
|
|
}
|
|
|
|
public RoomOpenHelper(@NonNull DatabaseConfiguration databaseConfiguration, @NonNull Delegate delegate, @NonNull String str) {
|
|
this(databaseConfiguration, delegate, "", str);
|
|
}
|
|
|
|
public RoomOpenHelper(@NonNull DatabaseConfiguration databaseConfiguration, @NonNull Delegate delegate, @NonNull String str, @NonNull String str2) {
|
|
super(delegate.version);
|
|
this.mConfiguration = databaseConfiguration;
|
|
this.mDelegate = delegate;
|
|
this.mIdentityHash = str;
|
|
this.mLegacyHash = str2;
|
|
}
|
|
|
|
/* JADX INFO: finally extract failed */
|
|
private void checkIdentity(SupportSQLiteDatabase supportSQLiteDatabase) {
|
|
if (hasRoomMasterTable(supportSQLiteDatabase)) {
|
|
String str = null;
|
|
Cursor query = supportSQLiteDatabase.query(new SimpleSQLiteQuery("SELECT identity_hash FROM room_master_table WHERE id = 42 LIMIT 1"));
|
|
try {
|
|
if (query.moveToFirst()) {
|
|
str = query.getString(0);
|
|
}
|
|
query.close();
|
|
if (!this.mIdentityHash.equals(str) && !this.mLegacyHash.equals(str)) {
|
|
throw new IllegalStateException("Room cannot verify the data integrity. Looks like you've changed schema but forgot to update the version number. You can simply fix this by increasing the version number.");
|
|
}
|
|
} catch (Throwable th) {
|
|
query.close();
|
|
throw th;
|
|
}
|
|
} else {
|
|
ValidationResult onValidateSchema = this.mDelegate.onValidateSchema(supportSQLiteDatabase);
|
|
if (onValidateSchema.isValid) {
|
|
this.mDelegate.onPostMigrate(supportSQLiteDatabase);
|
|
updateIdentity(supportSQLiteDatabase);
|
|
return;
|
|
}
|
|
StringBuilder L = a.L("Pre-packaged database has an invalid schema: ");
|
|
L.append(onValidateSchema.expectedFoundMsg);
|
|
throw new IllegalStateException(L.toString());
|
|
}
|
|
}
|
|
|
|
private void createMasterTableIfNotExists(SupportSQLiteDatabase supportSQLiteDatabase) {
|
|
supportSQLiteDatabase.execSQL("CREATE TABLE IF NOT EXISTS room_master_table (id INTEGER PRIMARY KEY,identity_hash TEXT)");
|
|
}
|
|
|
|
private static boolean hasEmptySchema(SupportSQLiteDatabase supportSQLiteDatabase) {
|
|
Cursor query = supportSQLiteDatabase.query("SELECT count(*) FROM sqlite_master WHERE name != 'android_metadata'");
|
|
try {
|
|
boolean z2 = false;
|
|
if (query.moveToFirst() && query.getInt(0) == 0) {
|
|
z2 = true;
|
|
}
|
|
return z2;
|
|
} finally {
|
|
query.close();
|
|
}
|
|
}
|
|
|
|
private static boolean hasRoomMasterTable(SupportSQLiteDatabase supportSQLiteDatabase) {
|
|
Cursor query = supportSQLiteDatabase.query("SELECT 1 FROM sqlite_master WHERE type = 'table' AND name='room_master_table'");
|
|
try {
|
|
boolean z2 = false;
|
|
if (query.moveToFirst() && query.getInt(0) != 0) {
|
|
z2 = true;
|
|
}
|
|
return z2;
|
|
} finally {
|
|
query.close();
|
|
}
|
|
}
|
|
|
|
private void updateIdentity(SupportSQLiteDatabase supportSQLiteDatabase) {
|
|
createMasterTableIfNotExists(supportSQLiteDatabase);
|
|
supportSQLiteDatabase.execSQL(RoomMasterTable.createInsertQuery(this.mIdentityHash));
|
|
}
|
|
|
|
@Override // androidx.sqlite.db.SupportSQLiteOpenHelper.Callback
|
|
public void onConfigure(SupportSQLiteDatabase supportSQLiteDatabase) {
|
|
super.onConfigure(supportSQLiteDatabase);
|
|
}
|
|
|
|
@Override // androidx.sqlite.db.SupportSQLiteOpenHelper.Callback
|
|
public void onCreate(SupportSQLiteDatabase supportSQLiteDatabase) {
|
|
boolean hasEmptySchema = hasEmptySchema(supportSQLiteDatabase);
|
|
this.mDelegate.createAllTables(supportSQLiteDatabase);
|
|
if (!hasEmptySchema) {
|
|
ValidationResult onValidateSchema = this.mDelegate.onValidateSchema(supportSQLiteDatabase);
|
|
if (!onValidateSchema.isValid) {
|
|
StringBuilder L = a.L("Pre-packaged database has an invalid schema: ");
|
|
L.append(onValidateSchema.expectedFoundMsg);
|
|
throw new IllegalStateException(L.toString());
|
|
}
|
|
}
|
|
updateIdentity(supportSQLiteDatabase);
|
|
this.mDelegate.onCreate(supportSQLiteDatabase);
|
|
}
|
|
|
|
@Override // androidx.sqlite.db.SupportSQLiteOpenHelper.Callback
|
|
public void onDowngrade(SupportSQLiteDatabase supportSQLiteDatabase, int i, int i2) {
|
|
onUpgrade(supportSQLiteDatabase, i, i2);
|
|
}
|
|
|
|
@Override // androidx.sqlite.db.SupportSQLiteOpenHelper.Callback
|
|
public void onOpen(SupportSQLiteDatabase supportSQLiteDatabase) {
|
|
super.onOpen(supportSQLiteDatabase);
|
|
checkIdentity(supportSQLiteDatabase);
|
|
this.mDelegate.onOpen(supportSQLiteDatabase);
|
|
this.mConfiguration = null;
|
|
}
|
|
|
|
@Override // androidx.sqlite.db.SupportSQLiteOpenHelper.Callback
|
|
public void onUpgrade(SupportSQLiteDatabase supportSQLiteDatabase, int i, int i2) {
|
|
boolean z2;
|
|
List<Migration> findMigrationPath;
|
|
DatabaseConfiguration databaseConfiguration = this.mConfiguration;
|
|
if (databaseConfiguration == null || (findMigrationPath = databaseConfiguration.migrationContainer.findMigrationPath(i, i2)) == null) {
|
|
z2 = false;
|
|
} else {
|
|
this.mDelegate.onPreMigrate(supportSQLiteDatabase);
|
|
for (Migration migration : findMigrationPath) {
|
|
migration.migrate(supportSQLiteDatabase);
|
|
}
|
|
ValidationResult onValidateSchema = this.mDelegate.onValidateSchema(supportSQLiteDatabase);
|
|
if (onValidateSchema.isValid) {
|
|
this.mDelegate.onPostMigrate(supportSQLiteDatabase);
|
|
updateIdentity(supportSQLiteDatabase);
|
|
z2 = true;
|
|
} else {
|
|
StringBuilder L = a.L("Migration didn't properly handle: ");
|
|
L.append(onValidateSchema.expectedFoundMsg);
|
|
throw new IllegalStateException(L.toString());
|
|
}
|
|
}
|
|
if (!z2) {
|
|
DatabaseConfiguration databaseConfiguration2 = this.mConfiguration;
|
|
if (databaseConfiguration2 == null || databaseConfiguration2.isMigrationRequired(i, i2)) {
|
|
throw new IllegalStateException(a.p("A migration from ", i, " to ", i2, " was required but not found. Please provide the necessary Migration path via RoomDatabase.Builder.addMigration(Migration ...) or allow for destructive migrations via one of the RoomDatabase.Builder.fallbackToDestructiveMigration* methods."));
|
|
}
|
|
this.mDelegate.dropAllTables(supportSQLiteDatabase);
|
|
this.mDelegate.createAllTables(supportSQLiteDatabase);
|
|
}
|
|
}
|
|
}
|