簡體   English   中英

Android Room:遷移未正確處理,Expected 和 Found 相等

[英]Android Room: Migration didn't properly handle, Expected and Found are equal

有人可以幫忙嗎? 預期的和發現的幾乎是相等的。 為什么房間在這里抱怨?

java.lang.RuntimeException: Exception while computing database live data.
        at androidx.room.RoomTrackingLiveData.refreshRunnable$lambda-0(RoomTrackingLiveData.kt:74)
        at androidx.room.RoomTrackingLiveData.lambda$UkyPj-RMUoTXOMbUuy5NWSwmo0E(Unknown Source:0)
        at androidx.room.-$$Lambda$RoomTrackingLiveData$UkyPj-RMUoTXOMbUuy5NWSwmo0E.run(Unknown Source:2)
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167)
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641)
        at java.lang.Thread.run(Thread.java:923)
     Caused by: java.lang.IllegalStateException: Migration didn't properly handle: emergency(hero.db.model.Emergency).
     Expected:
    TableInfo{name='emergency', columns={emergency_record_id=Column{name='emergency_record_id', type='INTEGER', affinity='3', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}, vehicle_plate=Column{name='vehicle_plate', type='TEXT', affinity='2', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}, device_id=Column{name='device_id', type='TEXT', affinity='2', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}, user_id=Column{name='user_id', type='INTEGER', affinity='3', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}, sent_to_cloud=Column{name='sent_to_cloud', type='INTEGER', affinity='3', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}, location=Column{name='location', type='TEXT', affinity='2', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}, id=Column{name='id', type='INTEGER', affinity='3', notNull=notNull, primaryKeyPosition=1, defaultValue='null'}, emergency_description=Column{name='emergency_description', type='TEXT', affinity='2', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}, timestamp=Column{name='timestamp', type='INTEGER', affinity='3', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}}, foreignKeys=[], indices=[]}
     Found:
    TableInfo{name='emergency', columns={emergency_record_id=Column{name='emergency_record_id', type='INTEGER', affinity='3', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}, vehicle_plate=Column{name='vehicle_plate', type='TEXT', affinity='2', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}, device_id=Column{name='device_id', type='TEXT', affinity='2', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}, user_id=Column{name='user_id', type='INTEGER', affinity='3', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}, sent_to_cloud=Column{name='sent_to_cloud', type='INTEGER', affinity='3', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}, location=Column{name='location', type='TEXT', affinity='2', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}, id=Column{name='id', type='INTEGER', affinity='3', notNull=notNull, primaryKeyPosition=1, defaultValue='null'}, emergency_description=Column{name='emergency_description', type='TEXT', affinity='2', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}, timestamp=Column{name='timestamp', type='INTEGER', affinity='3', notNull=notNull, primaryKeyPosition=0, defaultValue='null'}}, foreignKeys=[], indices=[]}

這是我的實體:


@Data
@AllArgsConstructor
@NoArgsConstructor
@Builder
@Entity(tableName = AppDatabase.TABLE_EMERGENCY)
public class Emergency {

    @ColumnInfo(name = "emergency_record_id")
    private Integer emergencyRecordId;

    @ColumnInfo(name = "vehicle_plate")
    private String vehiclePlate;

    @ColumnInfo(name = "device_id")
    private String deviceId;

    @ColumnInfo(name = "user_id")
    private Long userId;

    @ColumnInfo(name = "sent_to_cloud")
    @JsonIgnore
    private Boolean sentToCloud = false;

    @ColumnInfo(name = "location")
    private LocationRoute location;

    @PrimaryKey
    @ColumnInfo(name = "id")
    private Long id;

    @ColumnInfo(name = "emergency_description")
    private String emergencyDescription;

    @ColumnInfo(name = "timestamp")
    private Date timeStamp;
}

這是我的遷移:

 "CREATE TABLE IF NOT EXISTS " + TABLE_EMERGENCY + " (\n " +
                            "emergency_record_id    INTEGER                               ,\n " +
                            "vehicle_plate          TEXT                                  ,\n " +
                            "device_id              TEXT                                  ,\n " +
                            "user_id                INTEGER                               ,\n " +
                            "sent_to_cloud          INTEGER                               ,\n " +
                            "location               TEXT                                  ,\n " +
                            "id                     INTEGER     PRIMARY KEY       NOT NULL,\n " +
                            "emergency_description  TEXT                                  ,\n " +
                            "timestamp              INTEGER                               \n " +
                            " );"

有人可以幫忙嗎?

而不是試圖確定您的創建 SQL 的問題(不是它不正確,而是它不符合 Room 的期望) 我建議使用由 Room 生成的 SQL ,它是正確的。

添加緊急class 作為AppDatabase class 的@Database注釋中的實體之一后,編譯項目(CTRL+F9)。

  • 顯然你會這樣做。 從一開始就添加遷移時提到的一個步驟。

然后在Android 視圖中,找到java(generated) ,展開每個並查找AppDatabase_Impl例如:-

在此處輸入圖像描述

在此找到createAllTables (通常在頂部)並找到表的相應 _db.execSQL 例如:-

在此處輸入圖像描述

並將其用於遷移中的 SQL 例如:-

static Migration m1to2 = new Migration(1,2) {
    @Override
    public void migrate(@NonNull SupportSQLiteDatabase database) {
        /*
        database.execSQL(
        "CREATE TABLE IF NOT EXISTS " + TABLE_EMERGENCY + " (" +
                "emergency_record_id INTEGER," +
                "vehicle_plate TEXT," +
                "device_id TEXT," +
                "user_id INTEGER, " +
                "sent_to_cloud INTEGER, " +
                "location TEXT," +
                "id INTEGER PRIMARY KEY NOT NULL," +
                "emergency_description TEXT," +
                "timestamp INTEGER" +
                ");"
        );

         */
        database.execSQL("CREATE TABLE IF NOT EXISTS `emergency` (`emergency_record_id` INTEGER, `vehicle_plate` TEXT, `device_id` TEXT, `user_id` INTEGER, `sent_to_cloud` INTEGER, `location` INTEGER, `id` INTEGER, `emergency_description` TEXT, `timestamp` INTEGER, PRIMARY KEY(`id`))");
    }
};

為什么房間在這里抱怨?

這里有一些提示,但正如最初所說,是否值得深入研究。

  • 您的失敗代碼已被注釋掉(在刪除換行符之后),因為已經過測試:-
  • 我相信你會發現遷移並沒有失敗,當然也沒有必要花時間比較預期發現(我看不到任何明顯的東西)。
    • 您可能會注意到 Room 將表名和列名包含在``中的區別,這可以防止與 SQLite 關鍵字發生沖突(不是說我可以看到任何位置和時間戳,最有可能的候選者不是關鍵字
    • 另一個明顯的區別是id列是 INTEGER (沒有 NOT NULL)(很確定 PRIMARY KEY 編碼為列或表定義的一部分是好的)。
    • 如果您希望確定確切的問題,您可以運行從一個逐漸更改為另一個的測試。

正如您可能看到的,我已經使用了您可用的代碼,但進行了一些更改以適應其他代碼(例如 LocationRoute 類)以及刪除了一些注釋。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM