2017-01-04 2 views
0

Für meine Modelle von Server-API initialisieren i verwenden Konstruktor wie folgt aus:Subclass NSManagedObject zu leicht

@implementation MenuAPIModel 

-(instancetype)initWithServerData:(id)data{ 

    self = [super initWithServerData:data]; 
    return self; 
} 

-(void)performMapping{ 

    _basketId = self.serverData[@"basket_id"]; 
    _orderId = self.serverData[@"order_id"]; 
    _itemId = self.serverData[@"id"]; 
    _name = self.serverData[@"name"] == [NSNull null] ? @"" : self.serverData[@"persons"]; 
    _payedFrom = [self.dfDetail dateFromString:self.serverData[@"payed_from"]] == nil ? [self.dfBasic dateFromString:self.serverData[@"payed_from"]] : [self.dfDetail dateFromString:self.serverData[@"payed_from"]]; 
    _payedTill = [self.dfBasic dateFromString:self.serverData[@"payed_till"]] == nil ? [self.dfBasic dateFromString:self.serverData[@"payed_till"]] : [self.dfDetail dateFromString:self.serverData[@"payed_till"]]; 
    _persons = self.serverData[@"persons"] == [NSNull null] ? @"2-3" : self.serverData[@"persons"]; 
    _price = self.serverData[@"price"] == [NSNull null] ? @(0) : self.serverData[@"price"]; 
    _price3 = self.serverData[@"price3"] == [NSNull null] ? @(0) : self.serverData[@"price3"]; 
    _price12 = self.serverData[@"price12"] == [NSNull null] ? @(0) : self.serverData[@"price12"]; 
    _status = self.serverData[@"status"] == [NSNull null] ? @"not_payed" : self.serverData[@"persons"]; 
} 

So kann ich Objekt erstellen, mit einfach geschrieben: [MenuAPIModel initWithServerData:data];

Jetzt Unterklasse i NSManagedObject und Wunder, wie kann ich diese 4 Dateien, die XCode für mich erstellt hat, ableiten, um einen Konstruktor wie den obigen zu erstellen?

Antwort

1

Sie Art von Helfer erstellen können, die nach der Umsetzung haben kann (es ist nur Beispiel so habe ich Swift):

static open func createObject <T : NSManagedObject> (_ objectType : T.Type, record : Dictionary<String, Any>? = nil, context : NSManagedObjectContext) -> (T) 
{ 
    let newObject = NSEntityDescription.insertNewObject(forEntityName: String(describing: objectType), into: context) 

    // Error never occured 

    var typedNewObject = newObject as! T 

    guard let trueRecord = record 
    else 
    { 
     return typedNewObject 
    } 

    typedNewObject = updateObject(typedNewObject, record: trueRecord, context: context) 

    return typedNewObject 
} 

static open func updateObject <T : NSManagedObject> (_ object : T, record : Dictionary<String, Any>, context : NSManagedObjectContext) -> (T) 
{ 
    for (key, value) in record 
    { 
     setValue(value, key: key, object: object) 
    } 

    return object 
} 

static public func setValue (_ value : Any, key : String, object : NSManagedObject) -> (Void) 
{ 
    object.setValue(value, forKey: key) 
} 

Mit solchen Methoden können Sie dann eingeben:

let myNewObject = Helper.createObject(YourClassName.self, record: yourDictionary, context: yourContext) // Helper, or any other class name you give it. 

Ich hoffe, es ist nahe genug an dem, was Sie brauchen.

1

ich nicht vollständig verstehen, was Sie zu Unterklasse wollen, aber um CoreData Ihre Modelle zu verwenden müssen NSManagedObject Unterklasse, also, wenn Sie eine benutzerdefinierte Modellklasse Unterklasse möchten, die Sie geschrieben haben, muss diese Klasse NSManagedObject Unterklasse.

Jetzt erstellt die neue XCode-Vorlage für eine Klasse und eine Kategorie für jedes Modell, das Sie in xcdatamodel deklarieren. Und du hättest so etwas.

MenuAPIModel + CoreDataProperties.h

@interface MenuAPIModel (CoreDataProperties) { 
} 
@property(nonatomic, strong) NSNumber *basketId 
.....other properties that you have 
@end 

MenuAPIModel + CoreDataProperties.m

@implementation MenuAPIModel (CoreDataProperties) 
@dynamic basketId 
@dynamic ....other properties ... 
@end 

MenuAPIModel.h

@interface MenuAPIModel : NSManagedObject 
+(instancetype)initWithServerData:(id)serverData; 
@end 

MenuAPIModel.m

@implementation MenuAPIModel 

+(instancetype)initWithServerData:(id)serverData { 
    NSManagedObjectContext *context = ...get the current context... 
    MenuAPIModel *model = [NSEntityDescription insertNewObjectForEntityForName:NSStringFromClass([MenuAPIModel class])inManagedObjectContext:context]; 
    model.basketId = serverData[@"basket_id"]; 
    ...other parsing.... 
    return model; 
} 

Wie Sie sehen können, können Sie diese Klassen & Kategorien erstellt standardmäßig von XCode, durch Zugabe von nur einem zusätzlichen Verfahren verwenden können. Nur eine Erinnerung, kann nicht erstellt werden mit alloc] init];, es muss mit der NSManagedObjectContext erstellt werden.

+0

ich sehe, Sie setzen alle Logik in API-Modell. Aber ich möchte das Gegenteil tun: Erstelle und befülle das Kerndatenmodell basierend auf der fertiggestellten API Model Klasse. Zum Beispiel, wie man etwas wie [model initWithData: MenuAPIModell instance]; ? –

+0

@EvgeniyKleban Sie können das Kerndatenmodell nach Belieben auffüllen, der wichtige Teil ist, wie Sie das Codedatenmodell starten (genau wie ich). – danypata