Search code examples
pointersparse-platformxcode7pfquerypfquerytableviewcontrolle

IncludeKeys in PFQuery not returning all relational data


I am using PFQueryTableViewController to retrieve objects from Parse. This particular Parse class has three columns (group, category, client) which are pointers to other Parse classes. I want to use the includeKey option to bring in all object data for each of those pointer objects. However, when I run the code below, I do retrieve the basic data about each pointer column (like ObjectID), but none of the additional columns, like the "name" column of the Category class.

override func queryForTable() -> PFQuery {
        let query:PFQuery = PFQuery(className:self.parseClassName!)
        query.whereKey("client", equalTo: currentUser!)
        query.whereKey("status", equalTo: "Open")
        query.whereKey("expires", greaterThan: NSDate())
        query.includeKey("group")
        query.includeKey("category")
        query.includeKey("client")
        query.orderByAscending("expires")

        if(objects?.count == 0)
        {
            query.cachePolicy = PFCachePolicy.CacheThenNetwork
        }

        return query
    }

When my PFQueryTableViewController calls it's cellForRowAtIndexPath function, I have code to get the 'name' column of the category object brought in via includeKey

override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath, object: PFObject?) -> PFTableViewCell? {
    ...
    if let category = task["category"] as? PFObject {
        cell?.categoryLabel.text = String(category["name"])
    }
    ...
}

Running this retrieval of the category's 'name' value results in the following error and crash in Xcode:

*** Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: 'Key "name" has no data.  Call fetchIfNeeded before getting its value.'

This same error results when I attempt to access any additional columns of my pointer reference objects.

When I print(category) I appear to get a valid (but empty) object in my log, with no additional columns, like 'name':

<Category: 0x13c6ed870, objectId: mEpn6TH6Tc, localId: (null)> {
}

I have successfully tested calling the suggested fetch query to retrieve the missing pointer data for each pointer column, but (IMHO) the additional fetch defeats the purpose of the includeKey query option to limit API requests.

One thought I had was that a PFQuery may only allow one includeKey call. But, the research that I've done through both Parse's own iOS documentation and various developer posts do not indicate any limitation of max number of includeKeys a query can have.

Am I doing something unsupported by Parse or am I just syntactically not retrieving each pointers' object data the proper way?

I'm running the latest ParseUI as of this posting (1.1.6) and Parse (1.9.0) with Xcode 7.0.1

Thank you in advance for reading my post! I am only a couple months into learning iOS development, so this is both interesting and frustrating at the same time!


Solution

  • cell.category.text = object.objectForKey("category")!.objectForKey("name") as! String
    

    also, use the other "version" of cellForRowAtIndexPath, the one for PFQueryTableViewControllers:

      override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath, object: PFObject!) -> PFTableViewCell? {
        //4
    
        let cell = tableView.dequeueReusableCellWithIdentifier("yourCellIdentifier", forIndexPath: indexPath) as! yourCell
    
    
            return cell
    
    
    }
    

    this allows you to use the above syntax that I answered with.