2017-10-14 2 views
0

キャッシュされたバージョンのデータをデータベースから読み込む必要があります。同時に、新しいデータをサーバーに要求したいので、これをページごとに行います。 たとえば、最初のページの場合、データベースから最初のページデータのキャッシュバージョンを表示し、最初のページのみ新しいデータを要求したいとします。
Paging Libraryを使用してこれを達成したいと思います。
私はページのロード要求を傍受するのに役立つカスタムデータソースを作成しようとしましたが、その後、必要なページ番号と制限でネットワークコールを作成していましたが、キャッシュされたバージョンをデータベースから返しました。私はデータベースを更新しますが、それらの更新は反映されません。
(テーブル全体が無効化トラッカーを使用して変更されたために観察され、テーブルが無効になったときにデータソースが無効になると思うので、データソースにそのトラッカーを追加しても動作しません。一時的に作成することによって、その無効トラッカー事アウト:JobDaoでLivePagedListProvider getJobsを()して生成された実装をチェックする)ページングライブラリ - ネットワークからの要求中にキャッシュからデータを取り込みます

コード:

public class JobListDataSource<T> extends TiledDataSource<T> { 

private final JobsRepository mJobsRepository; 
private final InvalidationTracker.Observer mObserver; 


String query = ""; 

public JobListDataSource(JobsRepository jobsRepository) { 
    mJobsRepository = jobsRepository; 

    mObserver = new InvalidationTracker.Observer(JobEntity.TABLE_NAME) { 
     @Override 
     public void onInvalidated(@NonNull Set<String> tables) { 
      invalidate(); 
     } 
    }; 

    jobsRepository.addInvalidationTracker(mObserver); 
} 


@Override 
public int countItems() { 
    return DataSource.COUNT_UNDEFINED; 
} 

@Override 
public List<T> loadRange(int startPosition, int count) { 
    return (List<T>) mJobsRepository.getJobs(query, startPosition, count); 
} 


public void setQuery(String query) { 
    this.query = query; 
} 
} 

ジョブズリポジトリ機能:

public List<JobEntity> getJobs(String query, int startPosition, int count) { 
    if (!isJobListInit) { 
     JobList jobList = mApiService.getOpenJobList(
       mRequestJobList.setPageNo(startPosition/count + 1) 
       .setMaxResults(count) 
       .setSearchKeyword(query) 
     ).blockingSingle(); 
     mJobDao.insert(jobList.getJobsData()); 
    } 
    return mJobDao.getJobs(startPosition, count); 
} 

public void addInvalidationTracker(InvalidationTracker.Observer observer) { 
    mAppDatabase.getInvalidationTracker().addObserver(observer); 
} 

答えて

0

私はなぜそれが動作していない、私の最後に間違いがあったJobsRepositoryのJobDaoのgetJobsメソッドに間違ったパラメータを渡していた理解した。

JobDaoのgetJobs方法は、次のようになります:次のようにJobsRepositoryで

@Query("SELECT * FROM jobs ORDER BY jobID ASC LIMIT :limit OFFSET :offset") 
List<JobEntity> getJobs(int limit, int offset); 

とコールgetJobsは()行く:

return mJobDao.getJobs(startPosition, count); 

だから、最初のパラメータは制限と次の1でした相殺されたが、私は別の方法で回っていた。
今、それは魅力のように機能します!

さらに、JobsRepositoryのgetJobs()に変更を加えました。 最初にdbからデータを取得します(使用可能な場合)。必要に応じてネットワークに非同期要求を行います。 dbでデータが利用できない場合は、と呼び、ネットワークからデータを取得し、解析してdbを保存し、dbから最新のデータにアクセスして戻します。 だから、この関数は次のようなものです。それは、より読みやすくなり、それがあるとして

private void updateJobList(JobList jobList, int startPosition, boolean performInvalidation) { 
    JobListItemEntity[] jobs = jobList.getJobsData(); 

    Date currentDate = Calendar.getInstance().getTime(); 

    //tracks when this item was inserted in db, used in calculating whether data is stale 
    for (int i = 0; i < jobs.length; i++) { 
     jobs[i].insertedAt = currentDate; 
    } 

    mJobDao.insert(jobs); 

    if (performInvalidation) { 
     mJobListDataSource.invalidate(); 
    } 
} 

(私も(getJobsLimitOffsetにJobDaoでgetJobsを()と改名):

//you can even refactor this code so that all the network related stuff is in one class and just call that method 
public List<JobListItemEntity> getJobs(String query, int startPosition, int count) { 
    Observable<JobList> jobListObservable = mApiService.getOpenJobList(
      mRequestJobList.setPageNo(startPosition/count + 1) 
        .setMaxResults(count) 
        .setSearchKeyword(query)); 

    List<JobListItemEntity> jobs = mJobDao.getJobsLimitOffset(count, startPosition); 

    //no data in db, make a synchronous call to network to get the data 
    if (jobs.size() == 0) { 
     JobList jobList = jobListObservable.blockingSingle(); 
     updateJobList(jobList, startPosition, false); 
    } else if (shouldFetchJobList(jobs)) { 
     //data available in db, so show a cached version and make async network call to update data as this data is no longer fresh 
     jobListObservable.subscribe(new Observer<JobList>() { 
      @Override 
      public void onSubscribe(Disposable d) { 

      } 

      @Override 
      public void onNext(JobList jobList) { 
       updateJobList(jobList, startPosition, true); 
      } 

      @Override 
      public void onError(Throwable e) { 
       Timber.e(e); 
      } 

      @Override 
      public void onComplete() { 

      } 
     }); 
    } 
    return mJobDao.getJobsLimitOffset(count, startPosition); 
} 

updateJobList()のコードページングライブラリによって生成される方法も)

関連する問題