0

Does anyone have any idea why Xcode isn't recognizing the attributes I set for my entity?

In this block of code, the "authors" attribute works fine:

func createBook() {
        let entityDescription = NSEntityDescription.entityForName("Books", inManagedObjectContext: managedObjectContext!)
        let book = Books(entity: entityDescription!, insertIntoManagedObjectContext: managedObjectContext)
        book.name = bookName.text
        book.author = authorField.text
        managedObjectContext?.save(nil)
    }

Here, however, in a function in my TableViewController it says that "book" does not have an attribute "authors":

override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
        let cell = tableView.dequeueReusableCellWithIdentifier("Cell", forIndexPath: indexPath) as! UITableViewCell
        let book: AnyObject = newBookViewController.fetchedResultsController.objectAtIndexPath(indexPath)
        cell.textLabel?.text = book.name
        cell.detailTextLabel?.text = book.author
        return cell

Furthermore, when I add more attributes to my Books entity in the entity inspector, even the first function does not recognize them. Also, is this the proper way to save multiple attributes at once?

func bookFetchRequest() -> NSFetchRequest {
        let fetchRequest = NSFetchRequest(entityName: "Books")
        let nameSortDescriptor = NSSortDescriptor(key: "name", ascending: true)
        let authorSortDescriptor = NSSortDescriptor(key: "author", ascending: true)
        fetchRequest.sortDescriptors = [nameSortDescriptor]
        fetchRequest.sortDescriptors = [authorSortDescriptor]
        return fetchRequest
    }

1 Answer 1

1
  1. In order for the compiler to know that your book has an author, it has to know it a book.

    let book: AnyObject = newBookViewController.fetchedResultsController.objectAtIndexPath(indexPath)
    

    declares book as AnyObject, which is what objectAtIndexPath returns by default. Since you know it's a book, you can cast it as a book like this:

    let book = newBookViewController.fetchedResultsController.objectAtIndexPath(indexPath) as! Books
    
  2. Unfortunately, adding attributes in the identity inspector does not automatically add them to an existing NSManagedObject. Say you created the Books model without a genre field and you wanted to add that later, you would add it in the identity inspector and then add

    @NSManaged var genre: String
    

    to the Books class.

  3. If you want multiple sort descriptors on a fetch request (e.g. first sort by author, and for books by the same author, sort those by name) then you would do

    fetchRequest.sortDescriptors = [authorSortDescriptor, nameSortDescriptor]
    
Sign up to request clarification or add additional context in comments.

6 Comments

I think I have already told the compiler that it is dealing with a book by setting the entity description to Books. And if attributes aren't automatically added to the NSManagedObject, why was 'names' added without having to declare it as a variable in my code but the other's won't do the same?
Yeah, fetch requests do have an entity description, but for whatever reason, objectAtIndexPath "forgets" about that and always returns AnyObject by default. Have you tried casting it, did that work?
Hmm, when you first create a NSManagedObject from the identity inspector, it will usually take any attributes you've set up and turn them into NSManaged var instance variables. But if you then add further attributes, you have to add the instance variables yourself. If you're seeing something different, I'm not sure why
So I actually was able to get 'authors' to work by adding the variable and reinstalling the app. However, now a new attribute, numberOfPages, gives me the same error and I have tried all the same stuff. I don't care about saving the data that's stored in the simulator so would it be a good idea to just create a new project with a fresh data model with all my attributes already set up and copy in my code? I've tried creating a new entity to replace my old one and uninstalling the app in my current project and this does not work.
If it worked for authors, I don't know why it wouldn't work for numberOfPages. You really shouldn't have to start a new project just to add to the data model, usually uninstalling the app and rerunning it after the data model has changed l is good enough. Sorry, not sure why it's not working
|

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.