iOS/Parse.com-为PFQuery创建缓存

iOS/Parse.com-为PFQuery创建缓存,ios,caching,parse-platform,Ios,Caching,Parse Platform,我很难理解如何使用Parse缓存和检索对象。我试图创建一个查询,缓存对象,然后只检索缓存的对象,除非用户将对象保存到PFObject,否则我希望使用网络重新加载数据 这是我的尝试,也是我查询PFObjects的方式 //Gets the playlists from the desired user +(void)getPlaylistsForUser:(PFUser *)user withCompletion:(void(^)(NSMutableArray *playlists

我很难理解如何使用Parse缓存和检索对象。我试图创建一个查询,缓存对象,然后只检索缓存的对象,除非用户将对象保存到PFObject,否则我希望使用网络重新加载数据

这是我的尝试,也是我查询PFObjects的方式

    //Gets the playlists from the desired user
    +(void)getPlaylistsForUser:(PFUser *)user withCompletion:(void(^)(NSMutableArray *playlists))completion
    {
        PFQuery *userQuery = [PFQuery queryWithClassName:@"Playlists"];
        userQuery.cachePolicy = kPFCachePolicyCacheElseNetwork;
        [userQuery whereKey:@"userId" equalTo:[user objectId]];
        [userQuery findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) {
            if (!error){
                NSMutableArray *playlists = [[NSMutableArray alloc]init];
                playlists = [objects mutableCopy];
                    completion(playlists);
                }
        }];
    }

How would I go about notifying the query that there needs to be a network call instead of returning cached results?
编辑:我只用几行代码就获得了所需的功能

//Gets the playlists from the desired user
+(void)getPlaylistsForUser:(PFUser *)user withCompletion:(void(^)(NSMutableArray *playlists))completion
{
    PFQuery *userQuery = [PFQuery queryWithClassName:@"Playlists"];
    [userQuery whereKey:@"userId" equalTo:[user objectId]];
    userQuery.cachePolicy = kPFCachePolicyCacheElseNetwork;
    [userQuery findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) {
        if (!error){
            NSMutableArray *playlists = [[NSMutableArray alloc]init];
            playlists = [objects mutableCopy];
                completion(playlists);
            }
    }];
}
+ (void)saveTrack:(NSDictionary *)track toPlaylist:(PFObject *)playlist withCompletion:(void(^)(BOOL success))completion
{
    [playlist addObject:track forKey:@"playlist"];
    [playlist saveInBackgroundWithBlock:^(BOOL succeeded, NSError *error) {
        if (error)
        {
            NSLog(@"Error creating/saving playlist");
        }
        else{
            PFUser *current = [PFUser currentUser];
            PFQuery *playlistQuery = [PFQuery queryWithClassName:@"Playlists"];
            [playlistQuery whereKey:@"userId" equalTo:[current objectId]];
            [playlistQuery clearCachedResult];

            completion((BOOL)YES);
        }
    }];
}
本质上,我只是在需要查询重新加载数据时清除特定查询的缓存结果。我正在将查询的cachePolicy设置为KPFCachePolicyCacheLSenetwork


这是进行缓存的最佳方式吗?似乎正在按预期工作

看起来不错,但有点罗嗦。相反,如果不是查询本身,我会保留缓存策略的状态

@property (assign, nonatomic) PFCachePolicy cachePolicy;
// initialize this to kPFCachePolicyIgnoreCache (==0 so it will be by default)

// return a playlist query
+ (PFQuery *)playlistQueryForUser:(PFUser *)user {
    PFQuery *query = [PFQuery queryWithClassName:@"Playlists"];
    query.cachePolicy = self.cachePolicy;
    [query whereKey:@"userId" equalTo:[user objectId]];
    return query;
}
现在,您的代码只需要稍作更改,而且更好一点,imo,因为它保存了clear cache操作,并用缓存明确地表示了您的意图。请参阅此处显示diff的注释

//Gets the playlists from the desired user
+(void)getPlaylistsForUser:(PFUser *)user withCompletion:(void(^)(NSMutableArray *playlists))completion
{
    // diff here...
    PFQuery *query = [self playlistQueryForUser:user];
    [query findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) {
        if (!error){
            NSMutableArray *playlists = [[NSMutableArray alloc]init];
            playlists = [objects mutableCopy];
            completion(playlists);

            // diff here...
            self.cachePolicy = kPFCachePolicyCacheThenNetwork;
        }
    }];
}

+ (void)saveTrack:(NSDictionary *)track toPlaylist:(PFObject *)playlist withCompletion:(void(^)(BOOL success))completion
{
    [playlist addObject:track forKey:@"playlist"];
    [playlist saveInBackgroundWithBlock:^(BOOL succeeded, NSError *error) {
        if (error) {
            NSLog(@"Error creating/saving playlist");
        } else {
            // diff here: no need to rebuild the query, just change policy...  
            self.cachePolicy = kPFCachePolicyIgnoreCache;
            completion((BOOL)YES);
        }
    }];
}

谢谢你,这很有道理。为什么xcode不允许我写这一行query.cachePolicy=self.cachePolicy;所有这些代码都在我正在编写的API中。