Android Room:FOREIGN KEY约束失败(Sqlite代码787)

时间:2018-11-04 09:14:04

标签: java android android-room

我试图创建两个表dare_table和step_table并在插入步骤时遇到FOREIGN KEY约束失败错误(787)。

我关注了这些帖子,但没有成功:

我仍然是Room的新手,不胜感激!

Dare.class

@Entity(tableName = "dare_table",
indices = {@Index(value = {"stepList"}, unique = true),

public class Dare {

@PrimaryKey(autoGenerate = true)
public int id;

public Dare(String dareTitle, String stepList) {
    this.dareTitle = dareTitle;
    this.stepList = stepList;
}

public void setId(int id) {
    this.id = id;
}

private String dareTitle;

@ColumnInfo(name = "stepList")
private String stepList;

public int getId() {
    return id;
}

public String getDareTitle() {
    return dareTitle;
}

public String getStepList() {
    return stepList;
 }
}

Step.class

@Entity(tableName = "step_table",
    indices = {@Index(value = {"stepName"})},
    foreignKeys = @ForeignKey(
            entity = Dare.class,
            parentColumns = "stepList",
            childColumns = "stepName"
    ))

public class Step {

@PrimaryKey //Gets the same error with and without autoGenerate = true
public int id;

@ColumnInfo(name = "stepName")
private String stepName;

private boolean isCompleted;

public Step(String stepName, boolean isCompleted) {
    this.stepName = stepName;
    this.isCompleted = isCompleted;
}

public void setId(int id) {
    this.id = id;
}

public int getId() {
    return id;
}

public String getStepName() {
    return stepName;
}

public boolean isCompleted() {
    return isCompleted;
 }
}

错误日志中引用的doInBackground(在存储库类中)

    private static class InsertStepAsyncTask extends AsyncTask<Step, Void, Void> {

    private StepDao stepDao;

    private InsertStepAsyncTask(StepDao stepDao) {
        this.stepDao = stepDao;
    }

    @Override
    protected Void doInBackground(Step... steps) {
        stepDao.insert(steps[0]);
        return null;
    }
}

错误日志:

E/AndroidRuntime: FATAL EXCEPTION: AsyncTask #3
Process: com.kyperstudios.daretowork, PID: 9845
java.lang.RuntimeException: An error occurred while executing doInBackground()
    at android.os.AsyncTask$3.done(AsyncTask.java:365)
    at java.util.concurrent.FutureTask.finishCompletion(FutureTask.java:383)
    at java.util.concurrent.FutureTask.setException(FutureTask.java:252)
    at java.util.concurrent.FutureTask.run(FutureTask.java:271)
    at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:257)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1162)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:636)
    at java.lang.Thread.run(Thread.java:784)
 Caused by: android.database.sqlite.SQLiteConstraintException: FOREIGN KEY constraint failed (Sqlite code 787), (OS error - 0:Success)
    at android.database.sqlite.SQLiteConnection.nativeExecuteForLastInsertedRowId(Native Method)
    at android.database.sqlite.SQLiteConnection.executeForLastInsertedRowId(SQLiteConnection.java:818)
    at android.database.sqlite.SQLiteSession.executeForLastInsertedRowId(SQLiteSession.java:803)
    at android.database.sqlite.SQLiteStatement.executeInsert(SQLiteStatement.java:86)
    at androidx.sqlite.db.framework.FrameworkSQLiteStatement.executeInsert(FrameworkSQLiteStatement.java:51)
    at androidx.room.EntityInsertionAdapter.insert(EntityInsertionAdapter.java:64)
    at com.kyperstudios.daretowork.Data.StepDao_Impl.insert(StepDao_Impl.java:89)
    at com.kyperstudios.daretowork.Data.DareRepository$InsertStepAsyncTask.doInBackground(DareRepository.java:164)
    at com.kyperstudios.daretowork.Data.DareRepository$InsertStepAsyncTask.doInBackground(DareRepository.java:154)
    at android.os.AsyncTask$2.call(AsyncTask.java:345)
    at java.util.concurrent.FutureTask.run(FutureTask.java:266)
    at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:257) 
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1162) 
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:636) 
    at java.lang.Thread.run(Thread.java:784) 

1 个答案:

答案 0 :(得分:0)

您可以尝试插入名称为Dare类中不存在元素的外键的步骤。因此,您必须首先在步骤类中插入要在步骤列表中引用的带有stepList字段的Dare对象,然后才能成功插入步骤

daredao().insertAll(new Dare("dare_title1", steps[0].getStepName()));
stepdao().insertAll(steps[0]);