2014-03-13 96 views
2

我嘗試使用Restkit和RKPaginator加載api的所有頁面(我不知道加載第一頁之前的頁面數量)。在成功塊中加載下一頁時出現RKPaginator錯誤

1出10次嘗試,我得到以下錯誤

「NSInternalInconsistencyException」,理由是:「當一個已經在進行中無法執行的負載。」

出現此問題不提高,功能正在按預期

我使用下面的代碼:

- (void)loadAllPagesForEntity:(NSString*)entityName 
         success:(void (^)(RKPaginator *paginator, NSArray *objects, NSUInteger page))success 
{ 
    URObjectManager *objectManager = [URObjectManager sharedManager]; 

    NSString *requestString = [NSString stringWithFormat:@"%@?page=:currentPage&size=:perPage",entityName]; 

    RKPaginator* myPaginator = (RKPaginator*)[objectManager paginatorWithPathPattern:requestString]; 
    myPaginator.perPage = 50; // this will request /posts?page=N&per_page=20 

    [myPaginator setCompletionBlockWithSuccess:^(RKPaginator *paginator, NSArray *objects, NSUInteger page) 
    { 
      if ([paginator hasNextPage]) { [paginator loadNextPage]; } 
     else if (success) { success(paginator, objects, page); } 
    } 
    failure:^(RKPaginator *paginator, NSError *error) 
    { 
     NSLog(@"Failure: %@", error); 
    }]; 

    [myPaginator loadPage:0]; 
} 

此代碼是呼籲更多的實體:

[self loadAllPagesForEntity:@"entity1" success:nil]; 
[self loadAllPagesForEntity:@"entity2" success:nil]; 

...

[self loadAllPagesForEntity:@"entity n" success:nil]; 

我的程序崩潰,並且通過一個禁止以下斷言RKPaginator.m: L.158

NSAssert(self.isLoaded, @"Cannot determine hasNextPage: paginator is not loaded."); 

l.177

NSAssert(! self.objectRequestOperation, @"Cannot perform a load while one is already in progress."); 

這難道不是正確測試hasNextPage或在成功塊內執行loadNextPage? 什麼是正確的方法來做到這一點?

我曾嘗試沒有成功使用:

[paginator performSelector:@selector(loadNextPage) onThread:[NSThread currentThread] withObject:nil waitUntilDone:NO]; 

的延遲之後執行選擇校正問題,但不是一個可接受的解決方案。

+0

有多少,這些都是你在同一時間運行?你有沒有對操作隊列做任何事情? iOS版? OSX? – Wain

+0

我下載了20個關於ios7/ipad的約10個實體。我不使用操作隊列(但Restkit使用它在地下不是嗎?)。我也嘗試使用getPageAtPath和page作爲參數來初始化循環內的20個頁面的下載,並且不會遇到任何問題(除了頁面的數量是固定的)。 – nonobzh

+0

如果請求成功完成,那麼您應該能夠啓動下一頁。我會打開跟蹤日誌。記錄服務器響應。並改變'[objectManager.operationQueue setMaxConcurrentOperationCount:5];' – Wain

回答

0

看起來像RKPaginator.m中的錯誤(Restkit 0.23)。我會盡快在github上填寫請求。

看起來,成功回調和請求操作的完成不是在同一個線程中完成的。

所以,當成功被調用時,isLoaded並不總是被設置。

我改變了代碼,在執行成功回調之前總是調用操作的完成。 它爲我做了詭計。

評論L.198

// Add KVO to ensure notification of loaded state prior to execution of completion block 
//[self.objectRequestOperation addObserver:self forKeyPath:@"isFinished" options:0 context:nil]; 

L.221

[self.objectRequestOperation setCompletionBlockWithSuccess:^(RKObjectRequestOperation *operation, RKMappingResult *mappingResult) { 
    [self operationFinished]; 

    if (self.successBlock) { 
     self.successBlock(self, [mappingResult array], self.currentPage);    
    } 
} 

添加功能

-(void)operationFinished 
{ 
    RKObjectRequestOperation*oro = self.objectRequestOperation; 
    self.objectRequestOperation = nil; 

    self.loaded = (oro.mappingResult != nil); 
    self.mappingResult = oro.mappingResult; 
    self.error = oro.error; 
}