39

I have a little damn problem with CoreData. I want to insert a new Object, so I first have to create one. This is done by that code:

Challenges *newChallenge = [[Challenges alloc] init];
[newChallenge setName:@"TestChallenge"];
[newChallenge setRounds:[[NSNumber alloc] initWithInt:12]];
[newChallenge setShots:[[NSNumber alloc] initWithInt:5]];
[newChallenge setDate:[NSDate date]];

But however after the alloc init I get this error:

CoreData: error: Failed to call designated initializer on NSManagedObject class 'Challenges'

What the hack is going wrong?

Martin R
  • 529,903
  • 94
  • 1,240
  • 1,382
Bene
  • 636
  • 1
  • 8
  • 24

5 Answers5

60

I think the problem is that Challenges is a NSManagedObject class and you need the designated initializer:

initWithEntity:insertIntoManagedObjectContext:

instead of

Challenges *newChallenge = [[Challenges alloc] init];

Read More..

s4y
  • 50,525
  • 12
  • 70
  • 98
Leo Chapiro
  • 13,678
  • 8
  • 61
  • 92
30

In case you ask yourself "OK, so how to I get that entity?" (like I did), you do this by using the entityForName method like so:

NSEntityDescription *entity = [NSEntityDescription entityForName:@"Challenges" inManagedObjectContext:self.managedObjectContext];

Challenges *newChallenge = [[Challenge alloc] initWithEntity:entity insertIntoManagedObjectContext:self.managedObjectContext];

Hope this helps, this thread has helped me a lot!

pkamb
  • 33,281
  • 23
  • 160
  • 191
Jay Versluis
  • 2,062
  • 1
  • 19
  • 18
14

NSManagedObject cannot be just alloc/init like you would normally do with an NSObject. As a matter of fact the designated initializer is: initWithEntity:insertIntoManagedObjectContext:

Now, for the actual error, Apple states in the documentation that:

Important: This method is the designated initializer for NSManagedObject. You must not initialize a managed object simply by sending it init.

So, you could see that you need 2 things in order to initialize it, an NSEntityDescription (which entity you intend to instantiate) and an NSManagedObjectContext (the context that the new object will be created into).

Alladinian
  • 34,483
  • 6
  • 89
  • 91
4

Additionaly, if your Challenges class is NSManagedObject and date, rounds and shots are defined as its attributes you can add method:

-(void) awakeFromInsert {
     self.date = [NSDate date];
     self.rounds = @(12);
     self.shots = @(5);
}

Each new object will have defined those attributes from its birth.

StefanS
  • 1,089
  • 1
  • 11
  • 38
Łukasz
  • 773
  • 5
  • 23
4

Others have already stated why its not working. Here is how you can cut down on the boilerplate and make your code more readable:

@implementation NSManagedObject(MyPrivateAdditions)

+ (id)insertNewObjectInContext:(NSManagedObjectContext *)context
{
    return [NSEntityDescription insertNewObjectForEntityForName:self.className inManagedObjectContext:context];
}

@end

now you can do:

Challenges *newChallenge = [Challenge insertNewObjectInContext:context];
bernstein
  • 386
  • 1
  • 10