1
votes

I've been chasing a bug for a while now and I can't figure it out. I have a class that takes a bunch of parsed data and then calls a method to create new core data "Article" object for each element created from the parsed data. I've shown how I declare the NSManagedObjectContext below.

You will also see the method

Article.createFLOArticleWithStructure(element, inManagedObjectContext: self.articleContext)

I placed this method in an extension to clean up the code. The method is show below.

import Foundation

class FLODataHandler : NSObject, FLOConnectionHandlerDelegate, FLOParserHandlerDelegate, TriathleteParserHandlerDelegate, VeloNewsParserHandlerDelegate, CyclingNewsParserHandlerDelegate, RoadBikeActionParserHandlerDelegate, IronmanParserHandlerDelegate
{
    let appDelegate: AppDelegate = UIApplication.sharedApplication().delegate as! AppDelegate
    lazy var articleContext: NSManagedObjectContext = self.appDelegate.managedObjectContext!

    func floParserHandlerDidFinishParsing(parserHandler : FLOParserHandler)
    {
        for element in self.floParserHandler!.XMLParsedDataArray!
        {
            // The pubDate, tilte and link and indicator have been added to the titleLinkArray.  I will now add the data to a Core Data Entity
            // in the Article+NewsFeedArticle class.
            Article.createFLOArticleWithStructure(element, inManagedObjectContext: self.articleContext)
        }
    }

Extension Code

extension Article
{
    class func createFLOArticleWithStructure(articleStructure: DateTitleLink, inManagedObjectContext context: NSManagedObjectContext) -> (Article)
    {
        // Core data is much simpler in Swift.  I have not commented this code since I do not know if it's working yet.

        var article = Article()

        //var entity = NSEntityDescription("Article", inManagedObjectContext: context)
        let fetchRequest = NSFetchRequest(entityName: "Article")
        let predicate = NSPredicate(format: "feed == 'FLO Cycling' AND title == %@", articleStructure.title!)
        let sortDescriptor = NSSortDescriptor(key: "pubDate", ascending: true)
        fetchRequest.sortDescriptors = [sortDescriptor]

        // Set up NSError
        var fetchError : NSError?
        // When you perform a fetch the returned object is an array of the Atricle Entities.
        let fetchedObjects = context.executeFetchRequest(fetchRequest, error: &fetchError) as! [Article]

        if fetchedObjects.count > 1
        {
            println("Error! in Article+NewFeedArticle.swift")
        }
        else if fetchedObjects.count == 0
        {
            article = NSEntityDescription.insertNewObjectForEntityForName("Article", inManagedObjectContext: context) as! Article
            article.feed = "FLO Cycling"
            article.pubDate = articleStructure.date!
            article.title = articleStructure.title!
            article.link = articleStructure.link!
            article.theNewArticle = NSNumber(int: 1)

            var error : NSError?
            if(context.save(&error))
            {
                println(error!.localizedDescription)
            }
        }
        else if fetchedObjects.count == 1
        {
            article = fetchedObjects[fetchedObjects.endIndex - 1]
        }

        return article
    }

When I run the code I get stopped on the following line of the extension code and receive the following errors.

article = NSEntityDescription.insertNewObjectForEntityForName("Article", inManagedObjectContext: context) as! Article

CoreData: error: Failed to call designated initializer on NSManagedObject class 'FLOCycling1_1_1.Article' CoreData: warning: Unable to load class named 'Article' for entity 'Article'. Class not found, using default NSManagedObject instead. Could not cast value of type 'NSManagedObject_Article_' (0x7fe59c3515e0) to 'FLOCycling1_1_1.Article' (0x106139f70).

I've read online about using a prefix in the data model. I've added this to no avail. If you have any idea how I can fix this error I would appreciate the help.

ADDED****

Here is the Article.swift file on request.

import Foundation
import CoreData

@objc class Article: NSManagedObject
{
    @NSManaged var feed: String
    @NSManaged var link: String
    @NSManaged var pubDate: NSDate
    @NSManaged var theNewArticle: NSNumber
    @NSManaged var title: String
}

Take care,

Jon

1
Can you show us your class Article and confirm it's part of your target?Tommy
By target do you mean that it's included in the "Compile Sources" under "Build Phases"?jonthornham
I just noticed that the CoreData.framework is not included in the project. I used the cookie cutter Core Data Template. Do I have to add this myself?jonthornham
I added the CoreData.framework and this did not fix the issue. Just FYI.jonthornham

1 Answers

0
votes

The issue had to do with my declaration of Article in this line here.

var article = Article()

In the Swift version calling the line of code above allocates and initializes memory for the Article. In the Objective-C version of my code I called the following.

Article *article = nil;

While I am not sure why, allocating and initializing the Article is the issue. I found this post here about a similar error.

Failed to call designated initializer on NSManagedObject class 'ClassName'

To fix this I changed the code to

var article = Article?()

To be clear, I also changed the Article class to ProjectName.Article.

I hope this helps someone else.

Take care,

Jon