2017-01-09 8 views
0

Я довольно новичок в RxJava и использую его в Android.Chaining Модернизация и возврат только наблюдателя из локального sqlite

В моем презентаторе я пытаюсь получить мои данные с именами присвоений с помощью модификации с использованием RxJava.

Алгоритм очень прост, проверьте, сохранены ли какие-либо локальные назначения, если они не извлекаются с удаленного сервера, а затем попытайтесь извлечь из локального снова.

В настоящее время он выполняет выборку с удаленного сервера, если локальный sqlite возвращает 0 результатов. Я бы хотел, чтобы он возвращался только из локального sqlite, например, как мне его снова вызвать mRepository.query(new AssignmentSpecification.class) и вернуть только это?

ОБНОВЛЕНО К ТОКА РЕШЕНИЕ

restartableLatestCache(REQUEST_ASSIGNMENTS, 
     () -> { 

      Observable<List<Assignment>> assignmentsFromLocalDb = mRepository.query(new AssignmentSpecification()) 
        .flatMap(assignments -> assignments == null || assignments.isEmpty() ? 
         Observable.zip(mRetrofit.create(AssignmentService.class) 
              .GET(mAccessToken) 
              .flatMap(mRepository::add), 
            mRetrofit.create(EntityService.class) 
              .GET(mAccessToken) 
              .flatMap(mEntityRepository::add), 
            mRetrofit.create(FacilityService.class) 
              .GET(mAccessToken) 
              .flatMap(mFacilityRepository::add), 
            (dbAssignments, remoteEntities, remoteFacilities) -> dbAssignments) 
            .flatMap(dbAssignments -> mRepository.query(new AssignmentSpecification()) : Observable.just(assignments)); 

      return assignmentsFromLocalDb 
        .subscribeOn(Schedulers.io()) 
        .observeOn(mainThread()); 
     }, 
     (assignmentsFragment, response) -> assignmentsFragment.onSuccess(response), 
     (assignmentsFragment, throwable) -> assignmentsFragment.onError(throwable) 
    ); 

Repository например

@Override 
public Observable<List<Assignment>> query(Specification specification) { 
    final SqlSpecification sqlSpecification = (SqlSpecification) specification; 

    final SQLiteDatabase database = mOpenHelper.getReadableDatabase(); 
    final List<Assignment> assignments = new ArrayList<>(); 

    try { 
     final Cursor cursor = database.rawQuery(sqlSpecification.toSqlQuery(), new String[]{}); 

     for (int i = 0, size = cursor.getCount(); i < size; i++) { 
      cursor.moveToPosition(i); 

      assignments.add(mToAssignmentMapper.map(cursor)); 
     } 

     cursor.close(); 

     return Observable.just(assignments); 
    } finally { 
     database.close(); 
    } 
} 
+0

Зачем вам нужны объекты и сущности? –

+0

Они не предоставляются назначением и содержат метаданные, которые необходимы для назначения. Это произойдет только при первом запуске приложения и данных пока нет. – Rovdjuret

ответ

1

Предполагая репозиториев выглядит следующим образом:

interface Repository { 
    Observable<List<Assignment>> query(AssignmentSpecification assignmentSpecification); 
    Observable<List<Assignment>> add(List<Assignment> assignments); 
} 

Чем вы можете использовать этот код, чтобы получить данные:

Observable<List<Assignment>> assigmnets = mRepository.query(new AssignmentSpecification()) 
     .flatMap(assignments -> assignments == null || assignments.isEmpty() ? Observable.zip(mRetrofit.create(AssignmentService.class) 
         .GET(mAccessToken) 
         .flatMap(mRepository::add), 
       mRetrofit.create(EntityService.class) 
         .GET(mAccessToken) 
         .flatMap(mEntityRepository::add), 
       mRetrofit.create(FacilityService.class) 
         .GET(mAccessToken) 
         .flatMap(mFacilityRepository::add), 
       (apiAssignments, entities, facilities) -> apiAssignments) 
       .flatMap(apiAssignments -> mRepository.query(new AssignmentSpecification())) : Observable.just(assignments)); 
+0

Ничего себе, это было более чистым, чем мое решение, спасибо товарищу! – Rovdjuret

+0

Я нашел проблему, dbAssignments является результатом mRepository.query (new AssignmentSpecification()). Что дает мне значение null, мне нужно будет его снова запросить ПОСЛЕ того, как вызовы mRetrofit выполняются и добавляются в базу данных. Как это возможно? – Rovdjuret

+1

Вам нужно запросить еще раз в flatMap. Ответ отредактирован. –