When you write a static library which uses CoreData there's a big mess including a normal .xdatamodeld file into the project because you simply cannot just link its compiled version (.momd) into your binary, so it's better to create the whole NSManagedObjectModel
in the code like this:
NSAttributeDescription *dateAttribute = NSAttributeDescription.new;
dateAttribute.name = @"timestamp";
dateAttribute.attributeType = NSDoubleAttributeType;
dateAttribute.optional = NO;
dateAttribute.indexed = YES;
NSAttributeDescription *payloadAttribute = NSAttributeDescription.new;
payloadAttribute.name = @"payload";
payloadAttribute.attributeType = NSBinaryDataAttributeType;
payloadAttribute.optional = NO;
payloadAttribute.indexed = NO;
NSEntityDescription *entry = NSEntityDescription.new;
entry.name = entry.managedObjectClassName = NSStringFromClass(MyCustomEntry.class);
entry.properties = @[dateAttribute, payloadAttribute];
NSManagedObjectModel *mom = NSManagedObjectModel.new;
mom.entities = @[entry];
And everything is just perfect....
But! Wait, if I have more than one entity in my NSManagedObjectModel
and they are related (to-many, inversed, and so on), how in the world I gonna connect them in the code, like in example above, without that nice Xcode editor, where you make relationships with several mouse clicks?
Example
Imagine, we have a class MyCustomElement, which is almost the same as in MyCustomEntry from the code above. Now, here're their interfaces how they would appear if I used Xcode generation for entities:
@interface MyCustomEntry : NSManagedObject
@property (nonatomic, retain) NSNumber *timestamp;
@property (nonatomic, retain) NSData *payload;
@property (nonatomic, retain) MyCustomElement *element;
@end
@interface MyCustomElement : NSManagedObject
@property (nonatomic, retain) NSNumber * timestamp;
@property (nonatomic, retain) NSString * identifier;
@property (nonatomic, retain) NSSet *entries;
@end
@interface MyCustomElement (CoreDataGeneratedAccessors)
- (void)addEntriesObject:(MyCustomEntry *)value;
- (void)removeEntriesObject:(MyCustomEntry *)value;
- (void)addEntries:(NSSet *)values;
- (void)removeEntries:(NSSet *)values;
@end
What NSRelationshipDescription I need to create for them and how to init it?
Relationships are described by
NSRelationshipDescription
objects. The following code creates two entity descriptions for "MyCustomEntry", "MyCustomElement" with relationshipsentries
(MyCustomElement --> MyCustomEntry, to-many),element
(MyCustomEntry --> MyCustomElement, to-one), inverse ofentries
.Both entities have only a string attribute "identifier" (to save some lines of code).
Objective-c:
Swift (now updated for Swift 3/4):
I have tested this code and it seems to work, so I hope that it will be useful to you.