Android 连接表时房间未正确更新记录

Android Room not updating records properly when tables are joined

我有一个 DAO 具有以下查询方法:

@Dao
public interface QuoteDao {
    @Query("SELECT * FROM quotes")
    LiveData<List<Quote>> getAll();

    @Query("SELECT * FROM quotes " +
            "INNER JOIN categories ON categories.id = quotes.category_id " +
            "WHERE categories.selected = 1")
    LiveData<List<Quote>> getPreferred();

    @Update
    public void update(Quote quote);

}

Repository有以下方法:

public class QuoteRepository {
    private static final String TAG = "Repo/Quote";

    private final QuoteDao quoteDao;
    private LiveData<List<Quote>> quotes;

    private final long seed = System.currentTimeMillis();

    public QuoteRepository(Application application){
        quoteDao = DB.getInstance(application).quoteDao();
        quotes = Transformations.map(quoteDao.getAll(), quotes -> {
            List<Quote> list = new ArrayList<>(quotes);
            Collections.shuffle(list, new Random(seed));
            return list;
        });

        Log.d(TAG, "New instance created...");
    }

    public LiveData<List<Quote>> getQuotes(){
        return quotes;
    }

    public void updateQuote(Quote quote, QuoteRepository.CallBackListener listener){
        Future<?> future = DB.databaseWriteExecutor.submit(() -> quoteDao.update(quote));

        futureCallback(future, listener);
    }

    private void futureCallback(Future<?> future, QuoteRepository.CallBackListener listener){
        try {
            future.get();
            if(future.isDone())
                listener.onSuccess();
        } catch (ExecutionException e) {
            e.printStackTrace();
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }

    public interface CallBackListener{
        void onSuccess();
    }
}

我已经用 quoteDao.getAll() 初始化了 LiveData<List<Quote>> quotes 并洗牌了结果。 有了这个,当我尝试更新任何 Quote 对象时,它工作得很好。

但是当我用 quoteDao.getPreferred() 初始化 LiveData<List<Quote>> quotes 时,更新无法正常工作。这是我使用 getPreferred():

的方式
    public QuoteRepository(Application application){
        quoteDao = DB.getInstance(application).quoteDao();
        quotes = Transformations.map(quoteDao.getPreferred(), quotes -> {
            List<Quote> list = new ArrayList<>(quotes);
            Collections.shuffle(list, new Random(seed));
            return list;
        });

        Log.d(TAG, "New instance created...");
    }

预期行为 用例:用户可以 add/remove 作为 书签 来自 LiveData<List<Quote>> quotes 的任何 QuoteQuote 应该更新两个列表,即 quoteDao.getAll()quoteDao.getPreferred()

当前行为 它适用于 quoteDao.getAll()。 但是当用户尝试为 quoteDao.getPreferred() 中的任何 Quote 添加书签时,它的行为如下:

如何管理书签? 我在 quotes table 中有一列名为 bookmark,它存储 10为假

当前流程: Activity/Fragment > QuoteViewModel > QuoteRepository > QuoteDao

问题出在Query,我所有实体主键列被命名为id.

正在将父项(类别)的 ID 分配给子项(引用)。

我已经替换了这个:

@Query("SELECT * FROM quotes " +
        "INNER JOIN categories ON categories.id = quotes.category_id " +
        "WHERE categories.selected = 1")
LiveData<List<Quote>> getPreferred();

有了这个:

@Query("SELECT quotes.* FROM quotes " +
        "INNER JOIN categories ON categories.id = quotes.category_id " +
        "WHERE categories.selected = 1")
LiveData<List<Quote>> getPreferred();