2012-01-29 6 views
1

iPad 응용 프로그램에서 약 50 개의 파일을 다운로드하려면 ASINetworkQueue를 사용하고 있습니다. 사용자가 대기열을 일시 중지했다가 다시 시작할 수있는 방법을 찾고 있습니다.ASINetworkQueue 일시 중지 및 재시작

ASIHTTP 워드 프로세서

[request setAllowResumeForFileDownloads:YES]; 

참조하지만이 아닌 큐 레벨, 개별 요청 레벨에서 동작한다. ASINetworkQueue이 NSOperationQueue의 서브 클래스가 나는 또한

[queue setSuspended:YES]; 

을 시도하고이 큐를 일시 중지하는 동안이 진행중인 다운로드 영향을주지 않습니다이기 때문에 그들이 완료 한 다음 큐를 일시 정지 할 때까지, 그냥, 대기 이는 내 경우에 사용자가 버튼을 누르고 실제로 대기중인 큐와 몇 초 사이에 있음을 의미합니다. 이는 원하는 UI 경험이 아닙니다.

누구든지이 문제를 해결할 수있는 다른 방법을 제안 할 수 있습니까?

답변

0

내 솔루션 .. 먼저

- (void) pause 
{ 
    if(self.queue && self.queue.requestsCount>0) 
    { 
     NSLog(@"%@", self.queue.operations); 

     for (ASIHTTPRequest * req in self.queue.operations) { 
      req.userInfo = [NSDictionary dictionaryWithObject:@"1" forKey:@"ignore"]; 
     } 

     [self.queue.operations makeObjectsPerformSelector:@selector(cancel)]; 

     [self.queue setSuspended:YES]; 

     for (ASIHTTPRequest * req in self.queue.operations) { 
      ASIHTTPRequest * newReq = [[ASIHTTPRequest alloc] initWithURL:req.url]; 
      [newReq setDownloadDestinationPath:req.downloadDestinationPath]; 
      [newReq setTemporaryFileDownloadPath:req.temporaryFileDownloadPath]; 
//   [newReq setAllowResumeForFileDownloads:YES]; 
      [newReq setUserInfo:req.userInfo]; 
      [self.queue addOperation:newReq]; 

     } 

    } 
} 

- (void) resume 
{ 
    if(self.queue && self.queue.requestsCount>0) 
    { 
     [self _setupQueue]; 
     [self.queue go]; 
    } 
} 

- (void) _setupQueue 
{ 
    [self.queue setShouldCancelAllRequestsOnFailure:NO]; 
    [self.queue setRequestDidStartSelector:@selector(downloadDidStart:)]; 
    [self.queue setRequestDidFinishSelector:@selector(downloadDidComplete:)]; 
    [self.queue setRequestDidFailSelector:@selector(downloadDidFailed:)]; 
    [self.queue setQueueDidFinishSelector:@selector(queueDidFinished:)]; 
    [self.queue setDownloadProgressDelegate:self.downloadProgress]; 
    [self.queue setDelegate:self]; 
    self.queue.maxConcurrentOperationCount = 3; 
// self.queue.showAccurateProgress = YES; 
} 

는 일시 정지 기능은 실행중인 모든 작업을 취소하고 새 요청이 대기열로 밀어 다시 작성하십시오. 그런 다음 resume 함수는 대기열을 일시 중단합니다. setAllowResumeForFileDownloads를 요청하지 말아야합니다. 예, 그렇지 않으면 totalBytesToDownload가 wrong..elf를 계산합니다. allowResumeForFileDownloads = NO 일 경우 해당 값은 대기열에있는 요청 수와 같습니다.

내 요청 실패 처리기입니다. 파일 다운로드가 실패하면 다시 시도해 봅니다. 하지만 내가 요청을 취소 할 때, 재시도 메커니즘이 호출 될 것입니다. 그래서 userInfo (ignore : true)를 설정하여 객체가 요청하지 않도록합니다.

- (void) downloadDidFailed:(ASIHTTPRequest *)req 
{ 
    NSLog(@"request failed"); 
    NSLog(@"%d", self.queue.requestsCount); 

    if(![self.queue showAccurateProgress]) 
    { 
     [self.queue setTotalBytesToDownload:[self.queue totalBytesToDownload]-1]; 
     NSLog(@"totalBytesToDownload=%lld", self.queue.totalBytesToDownload); 
    } 

    NSDictionary * userInfo = req.userInfo; 
    if([[userInfo valueForKey:@"ignore"] boolValue]) return; // ignore retry 

    int retryTimes = [[req.userInfo objectForKey:@"retryTimes"] intValue]; 
    if(retryTimes<kMU_MaxRetry) 
    { 
     ++ retryTimes; 
     NSLog(@"retry %d", retryTimes); 
     ASIHTTPRequest * newReq = [ASIHTTPRequest requestWithURL:req.url]; 
     [newReq setDownloadDestinationPath:req.downloadDestinationPath]; 
     [newReq setTemporaryFileDownloadPath:req.temporaryFileDownloadPath]; 
     newReq.userInfo = [NSDictionary dictionaryWithObject:[NSString stringWithFormat:@"%d", retryTimes] forKey:@"retryTimes"]; 
     [self.queue addOperation:newReq]; 

     NSLog(@"%d", self.queue.requestsCount); 
    }else{ // reach max retry, fail it 
     [self.failures addObject:req]; 
    } 
} 

더 나은 해결책이 있는지 확실하지 않습니다. 도움이 될 수 있기를 바랍니다.

관련 문제