ios - 对许多请求进行排队,然后根据添加的时间进行排序,但项目最终会根据从请求中收到的时间进行排序

标签 ios objective-c core-data afnetworking nsfetchedresultscontroller

我正在使用 AFNetworking并使用操作队列(类似于 NSOperationQueue)将一堆请求排队到 Clear Read API .

我基本上有一个 URL 数组,我根据每个请求创建单独的请求,将每个请求排入队列,然后批量执行请求。它们返回,一次一个,然后我添加时间戳,然后将它们添加到核心数据,这是我的 TableView 的源,因此 TableView 被填充。

仅当项目成功返回时才会发出时间戳。这意味着项目将根据返回时间而不是原始 URLs 数组的顺序进行排序。因此,返回时间较短的请求(API 处理的文本较少)的时间戳较早,因此被认为比由于文本量较大而时间戳较晚的项目更早。就正确排序而言,情况显然不是这样。

最后,即使我有一组按正确顺序调用 API 的 URL,我的 TableView 也会根据 API 返回项目的时间进行排序。

这是我的代码:

- (void)addArticlesFromURLs:(NSArray *)URLs fromSource:(NSString *)source {
    // Restrict amount of operations that can occur at once
    [[AFClearReadClient sharedClient].operationQueue setMaxConcurrentOperationCount:3];

    // Create an array to hold all of our requests to make
    NSMutableArray *requestOperations = [[NSMutableArray alloc] init];

    for (NSString *URL in URLs) {       
        // Create the request from the article's URL
        NSMutableURLRequest *request = [[AFClearReadClient sharedClient] requestWithMethod:@"GET" path:[NSString stringWithFormat:@"/v1/clear?url=%@&format=json", URL] parameters:nil];

        // Create the request operation and specify behaviour on success and failure
        AFHTTPRequestOperation *requestOperation = [[AFClearReadClient sharedClient] HTTPRequestOperationWithRequest:request
                                                                      success:^(AFHTTPRequestOperation *operation, id responseObject) {
                                                                            // Get the item NSDictionary from the JSON responseObject
                                                                            NSDictionary *item = [responseObject objectForKey:@"item"];

                                                                            // Get the values needed to create an article
                                                                            NSString *title = [item objectForKey:@"title"];
                                                                            NSString *URL = [item objectForKey:@"link"];
                                                                            NSString *body = [item objectForKey:@"description"];

                                                                            // Replace HTML entities with their actual characters
                                                                            title = [title stringByReplacingOccurrencesOfString:@"&" withString:@"&"];

                                                                            // Remove all HTML and formatting from body so only plain-text remains
                                                                            body = [self removeHTMLAndFormatting:body];

                                                                                // Add it to CoreData if there's actual content (easiest way to tell is checking body)
                                                                            if (![body isEqualToString:@""]) {
                                                                                NSManagedObjectContext *context = self.managedObjectContext;
                                                                                ArticleInfo *articleInfo = [NSEntityDescription insertNewObjectForEntityForName:@"ArticleInfo" inManagedObjectContext:context];
                                                                                articleInfo.source = source;
                                                                                articleInfo.body = body;
                                                                                articleInfo.title = title;
                                                                                articleInfo.url = URL;
                                                                                articleInfo.timeStamp = [NSDate date];

                                                                                NSError *error;
                                                                                [context save:&error];
                                                                            }
                                                                      }
                                                                      failure:^(AFHTTPRequestOperation *operation, NSError *error) {
                                                                            NSLog(@"Request operation error: %@", error);
                                                                      }];

        // Save the request operation in an NSArray so all can be enqueued later
        [requestOperations addObject:requestOperation];
    }

    // Enqueue the request operations
    [[AFClearReadClient sharedClient] enqueueBatchOfHTTPRequestOperations:requestOperations progressBlock:^(NSUInteger numberOfFinishedOperations, NSUInteger totalNumberOfOperations) {
        [self.tableView reloadData];
    } completionBlock:^(NSArray *operations) {
        [self.tableView reloadData];
    }];
}

我将如何改变它,以便我的 tableview 中的项目按正确的顺序排列(最新的在最前面)?

最佳答案

使用 userInfo

AFHTTPRequestOperationAFURLConnectionOperation 的子类,AFURLConnectionOperation 声明了一个userInfo 字典,不被触及就通过。它的目的是让您添加操作完成时需要使用的任何数据。在将操作添加到队列之前,请执行以下操作:

[requestOperation setUserInfo:@{ @"timestamp" : [NSDate date] };

在你的完成 block 中获取它作为

NSDate *timestamp = [operation userInfo][@"timestamp"];

时间戳将反射(reflect)操作添加到队列的顺序。

关于ios - 对许多请求进行排队,然后根据添加的时间进行排序,但项目最终会根据从请求中收到的时间进行排序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17459599/

相关文章:

iphone - 如何通过iphone app中的代码获取用户的当前位置?

iOS 解析错误 : Attempted to change an objectId to one that's already known to the Offline Store

objective-c - iOS8 和 iOS7 推送通知负载

ios - objective-C 中的 "@TRUE"

ios - Core Data "The Database appears corrupt"——是什么导致了这个错误?

swift - 在 UITableViewCell 中按下按钮后获取 NSManagedObject 的一个属性

iphone - ios 查找所有保存的文件

IOS - 从 UIBeizerPath 获取二进制掩码(位掩码)

ios - NSDirectoryEnumerator 迭代元素无法比较后缀

ios - "fatal error: unexpectedly found nil while unwrapping an Optional value"尝试将谓词与关系对象一起使用时