Coder Social home page Coder Social logo

easymapping's People

Contributors

adrian-gierakowski avatar alejandro-isaza avatar armandzwan avatar artfeel avatar basitali avatar belkevich avatar chrisalbert avatar dentelezhkin avatar dependabot[bot] avatar filmhomage avatar florianbuerger avatar ilyapuchka avatar jack-s avatar jfmorin avatar k-be avatar krivoblotsky avatar lucasmedeirosleite avatar lucasmedeirossagarana avatar marrliss avatar mitrenegade avatar pomozoff avatar readmecritic avatar rock88 avatar sebastianludwig avatar siuying avatar thekie avatar toolboxash avatar uncommon avatar xbeg9 avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

easymapping's Issues

An exception in the last version

Hello!

For some reason isKindOfClass doesn't work as expected and exceptions raises during mapping objects from json in method arrayOfObjectsFromExternalRepresentation:withMapping:

id mapping = [SPTariff objectMapping];
NSLog(@"%@ %d", mapping, [mapping isKindOfClass:[EKObjectMapping class]]);
NSParameterAssert([mapping isKindOfClass:[EKObjectMapping class]]);
console : <EKObjectMapping: 0x15e3fce0> 0

Array of Ids

I have next JSON for Game object
{
"objectId": 2,
"title": "Game 1",
"gameTypes": [ 1,2,3 ],
}

GameTypes already in database. I just need to connect these game types to received Game object.

Is there a way to map such JSON?

I have tried
[mapping hasManyMapping:[GameType mapping] forKey:gameTypes];
but it crushed, because it tried to get objectId from NSNumber.

In mapping for GameType I provide primaryKey = @"objectId". Is it possible to use this property as a key for each id in array?

Recursive relation for Core Data

I tried to add recursive relation to a Core Data object.

For example, a Person having a relative which is another Person. This work for regular objects but not Core Data managed objects.

In the example project, I tried to add a relative to ManagedPerson. The test crashed at [EKCoreDataImporter importerWithMapping:externalRepresentation:context:].

Is this a limitation of EasyMapping right now, or I'm doing anything wrong?

EasyMapping processing on background thread

I am using EasyMapping to process a relatively large JSON and it seems to be slowing down the main thread slightly. An activity indicator animation we use visibly slows down, and I'm 90% sure it is because of processing the JSON on the main thread.

I tried to use dispatch_async to run easymapping on a background thread with a child MOC, but I then get a multithread violation. It seems to happen in EKCoreDataImporter:fetchExistingObjectsForMapping:

NSArray * existingObjects = [self.context executeFetchRequest:fetchRequest error:NULL];

Has any work been done to run EasyMapping on a background thread? Or should EasyMapping be fast enough on the main thread?

incompatible pointer type sending "EKManagedObjectMapping" to parameter of type EKObjectMapping

I have created a mapping provide class for myObjects mapping as class methods as like as your provided example.
but XCODE issues a warning as I've title of this issue. thats because I've sending a reference to self in the static method.

  • (EKManagedObjectMapping *)personWithCarMapping
    {
    return [EKManagedObjectMapping mappingForEntityName:NSStringFromClass([ManagedPerson class])
    withBlock:^(EKManagedObjectMapping *mapping) {
    [mapping mapFieldsFromDictionary:@{ @"id": @"personID" }];
    [mapping mapFieldsFromArray:@[@"name", @"email"]];
    [mapping hasOneMapping:[self carMapping] forKey:@"car"];
    mapping.primaryKey = @"personID";
    }];
    }

so do you have any idea to solve this warning?

Provide NSManagedObjectContext or self in mappings

I'm currently having an issue that I think could be solved by providing either the context, or a reference to the newly created object in value blocks.

Consider this example:

Class A has a one-to-one relationship pointing to class B.
The JSON given for class A looks like this:

{
  "description": "foo",
  "object_b_id": 1
}

To make this relationship in the mapping I would like to be able to do a query like:

[mapping mapKey:@"object_b_id" toField:@"objectB" withValueBlock:^(NSString *key, id value, id this)
{
    return [B findByID:value inContext:this.managedObjectContext];
}

Currently this doesn't seem to be possible since there is no access inside any blocks for self, or the context being used to create the new object. This could also be done with something like:

NSFetchRequest *request = ...;
// implicitly set request.fetchLimit = 1
[mapping hasOneMapping:BMapping forKey:@"object_b_id" forField:@"objectB" withFetchRequest:request];

Parsing nested JSON withRootPath

My JSON looks like this
{
"@odata.context": "http://website.com/lmapi/api/odata/$metadata#Customers",
"value": [{
"Id": 1,
"FirstName": "Bill",
"LastName": "Smith",
"Email": "[email protected]",
"Phone": "3031234567",
"CustomerStatusId": 2,
"Created": "2014-08-07T16:57:27.103Z",
"Modified": "2014-08-18T12:06:49.587Z",
"Active": true,
"AppInstalled": false
}]
}

I'm using this to parse it:

return [EKObjectMapping mappingForClass:[Customer class] withRootPath:@"value" withBlock:^(EKObjectMapping *mapping) {
    [mapping mapFieldsFromArray:@[@"Id", @"CustomerStatusId", @"LastName", @"FirstName", @"Email", @"AppInstalled", @"Phone"]];
}];

But it fails. what am I doing wrong?

Mapping Composite Object

your frameWork is great specially its synchronization. but have a problem
I have a composite object (graph) like parent children.

person {
id
name
parent
}

parent and child are of type person
parent can have many children, every child has a parent. here I have only one entity person. with one relationship: Parent.
so when I try to map JSON to such object, the EasyMapping stuck in infinite loop recursively calls for personMapping and crashes,
so what to do?

`+ (FEMManagedObjectMapping *)personMapping
{
    return [FEMManagedObjectMapping mappingForEntityName:@"Restaurant" configuration:^(FEMManagedObjectMapping *mapping) {
        [mapping setPrimaryKey:@personID"];
        [mapping addAttributeMappingDictionary:@{
                                                 @"personID":@"ID",
                                                 @"name":@"Name"
                                                 }];

        [mapping addRelationshipMapping:[self personMapping] forProperty:@"parent" keyPath:@"parent"];

    }];
}

Bool from string parsing

Im getting -[__NSCFString charValue]: unrecognized selector sent to instance 0x7b160510
when trying to parse @"true" to BOOL property. Any workarounds except custom mapping?

What do you think about detection of the one or many relationships?

Something like this:

[mapping.recursiveMapping enumerateKeysAndObjectsUsingBlock:^(id key, id fieldName, BOOL *stop) {
        id representationForParsing = [representation valueForKeyPath:key];
        if ([representationForParsing isKindOfClass:[NSArray class]])
        {
            NSArray *parsedArray = [self arrayOfObjectsFromExternalRepresentation:representationForParsing withMapping:mapping];
            id parsedObjects = [EKMapper convertPropertyArray:parsedArray forObject:object withPropertyName:fieldName];
            [object setValue:parsedObjects forKeyPath:fieldName];
        }
        else if ([representationForParsing isKindOfClass:[NSDictionary class]])
        {
            id result = [self objectFromExternalRepresentation:representationForParsing withMapping:mapping];
            [object setValue:result forKeyPath:fieldName];
        }
        else if (representationForParsing == nil || representationForParsing == [NSNull null])
        {
            [object setValue:nil forKeyPath:fieldName];
        }
    }];

EKSerialiser no longer works for Managed Objects

EKPropertyMapping now has separate value and reverse blocks for managed objects.

@Property (nonatomic, strong) EKManagedMappingReverseValueBlock managedReverseBlock;

When serialising in..

  • (void)setValueOnRepresentation:(NSMutableDictionary *)representation fromObject:(id)object withPropertyMapping:(EKPropertyMapping *)propertyMapping

we have..

    if (propertyMapping.reverseBlock) {
        returnedValue = propertyMapping.reverseBlock(returnedValue);
    }

So the managed object reverse block does not get called.

We can't call the managed version here because it requires an NSManagedObjectContext.

Im not sure of the best way forward here, I'm not sure why we really need to pass the managedObjectContext when serialising, so the signature could be changed and then the serialiser can try..

    if (propertyMapping.reverseBlock) {
        returnedValue = propertyMapping.reverseBlock(returnedValue);
    }else if (propertyMapping.manageReverseBlock) {
        returnedValue = propertyMapping.reverseBlock(returnedValue);
    } 

Alternatively we could have an EKManagedSeraliser, subclass EKSerializer and override setValueOnRepresentation so that it uses the managedReverseBlock..

Respect mutable properties

Currently, mutable properties (NSMutableDictionary, NSMutableArray, NSMutableSet) get mapped to their immutable counterparts when an object is instantiated from a json dict. Ideally, EasyMapping would know to instantiate the mutable versions of these properties.

FastEasyMapping merge

Here i would like to discuss major changes of FastEasyMapping, so we can build roadmap of merge.

Map many objects to NSMutableArray

Perhaps I'm just missing something fairly basic, but is there a way to have EasyMapping return an NSMutableArray instead of an Array?

For example in the given example on the project page if instead of

 @property (nonatomic, strong) NSArray *phones;

You had

 @property (nonatomic, strong) NSMutableArray *phones;

What would use instead of the following

[mapping hasManyMapping:[self phoneMapping] forKey:@"phones"];

Should I somehow be making use of the

[mapping mapKey:@"" toField:@"" withValueBlock:...

method?

Jack

Object serialization when JSON key and property name differ not working

Problem: The app crashes with NSInvalidArgumentException because an unrecognized selector is sent, when serializing object with different json key and property name.

Steps to reproduce:

  1. Create an object with a property of another object or an array
  2. Write mapping for the container object using hasManyMapping:forKey:forField: where key and field values differ
  3. Try to serialize an object.

Reason:
In setHasManyMappingObjectOn:withPropertyName:withObjectMapping:fromObject: and
setHasOneMappingObjectOn:withPropertyName:withObjectMapping:fromObject: a key of corresponding mapping dictionary is used for a propertyName variable. When we set mapping with hasManyMapping:forKey:forField: the object has no property named with that key.

Crash with NSNull

If change Person.json to:
{
"name": "Lucas",
"email": "[email protected]",
"gender" : "male",
"car": {
"model": "i30",
"year": "2013"
},
"phones": null
}

you will get crash with
*** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[NSNull countByEnumeratingWithState:objects:count:]: unrecognized selector sent to instance 0x17a7678'

1.0 Roadmap

  • Change signature of CoreData mapping block (#57)
  • Provide relevant examples with new syntax on Objective-C
  • Examples on Swift

errors after update to 0.6.1

i have this mapping for managed object NewsEntry

+ (EKManagedObjectMapping *)mapping {
    return [EKManagedObjectMapping mappingForEntityName:kNewsEntry withBlock:^(EKManagedObjectMapping *mapping) {
        [mapping setPrimaryKey:@"id"];
        [mapping mapFieldsFromArray:@[@"id",@"title", @"unread", @"author"]];
        [mapping mapKey:@"updated" toField:@"updated" withValueBlock:^id(NSString *key, id value) {
            NSString *updatedString = (NSString *) value;
            return [NSDate dateWithTimeIntervalSince1970:([updatedString doubleValue] / 1000)];
        }];
        [mapping mapKey:@"crawled" toField:@"published" withValueBlock:^id(NSString *key, id value) {
            NSString *crawledString = value;
            return [NSDate dateWithTimeIntervalSince1970:([crawledString doubleValue] / 1000)];
        }];
    }];
}

When i trying to parse json with

 NSArray *entries = [EKManagedObjectMapper arrayOfObjectsFromExternalRepresentation:itemArray withMapping:[NewsEntry mapping] inManagedObjectContext:context];

i get this error:

'[<NewsEntry 0x10cf379c0> valueForUndefinedKey:]: the entity NewsEntry is not key value coding-compliant for the key "crawled".'

Before update my mapping worked correctly.
Is this something wrong with my mapping, or this is a bug?

And when i adding to mapping

 [mapping hasManyMapping:[NewsCategory mapping] forKey:@"categories"];

i get this error

[_NSFaultingMutableSet ek_flattenedArray]: unrecognized selector sent to instance 0x10cfbe300'

Sorry for my english

nil values need to replace existing values for dates

When I create a date mapper, if the json contains an explicit null value for that property, dates currently don't replace the existing value with a null value. This may be true of other mappings too, but I've explicitly tested it for when we have a date.

Mac OS X support

@lucasmedeirosleite Could you please add Mac OS X support?

It seems code doesn't need any changes, the only thing that needs to change is podspec, you can simply replace

s.platform = :ios, '5.0'
s.ios.deployment_target = '5.0'

with

s.ios.deployment_target = '5.0'
s.osx.deployment_target = '10.7'

Inserted Objects not cached in Core Data Importer

I'm having an issue with duplicates during import of data. The Core Data Importer fetches existing records before importing and stores it into a cache to detect if a record should be updated or inserted. But when the importer inserted a new record, it never gets into this cache. That means that if you import an array of data that contains a reference to a certain record more than once you'll end up with duplicates.

In my case my data looks like this:

[{
   id: 1,
   event: {
      id: 1
      ...
   }
   ...
},{
   id: 2,
   event: {
      id: 1
      ...
   }
   ...
}] 

Importing this will end up in a duplicate for Event with id 1.

I would suggest to add a method like this to EKCoreDataImporter:

- (void)cacheObject:(NSManagedObject *)object withMapping:(EKManagedObjectMapping *)mapping 
{
    NSMutableDictionary *entityObjectsMap = self.fetchedExistingEntities[mapping.entityName];
    entityObjectsMap[[object valueForKey:mapping.primaryKey]] = object;
    self.fetchedExistingEntities[mapping.entityName] = entityObjectsMap;
} 

And then in EKManagedObjectMapper in the method objectFromExternalRepresentation:withMapping: add the a new object to the cache. Probably same needs to be done in syncArrayOfObjectsFromExternalRepresentation:withMapping:fetchRequest:.

Do you agree with this?

EKMapper retaining objects

Hi guys,

Just notice that the following method is retaining the objects, do you have the same issue?
+[EKMapper objectFromExternalRepresentation:withMapping:]

Kind Regards,
fnxpt

Validation

Do we need any validation during mapping? Like getting error back from EKMapper with list of invalid keys and values?

How to handle flat JSON objects?

I got a stupid JSON API like this:

[
    {
        "messageId": 22,
        "message": "Hi there",
        "userid": 100,
        "username": "Jon Doe",
    },
    {
        "messageId": 23,
        "message": "Hi Again",
        "userid": 100,
        "username": "Jon Doe",
    }
]

It's flat, but I want to store it into core data with relations, an user has many messages, a message belongs to one user, how can I do that with EasyMapping? The framework doesn't seem quite happy when I try to omit the key in

[mapping hasOneMapping:fromUserMappingWithDictionary(dictionary)
                                       forKey:@""
                                     forField:@"message"];

Support for managed objects

It would be nice to have support for CoreData managed objects. It would be a simple change, just add a method to EKMapper and a property to EKObjectMapper (or having a EKManagedObjectMapper class):

+ (id)managedObjectFromExternalRepresenation:(NSDictionary *)externalRepresentation withMapping:(EKObjectMapping *)mapping withManagedObjectContext:(NSManagedObjectContext*)moc {
    NSManagedObject* object = [NSEntityDescription insertNewObjectForEntityForName:mapping.entityName inManagedObjectContext:moc];
    return [self fillObject:object fromExternalRepresentation:externalRepresentation withMapping:mapping];
}

bool's are not being serialized

When serializing an object EKSerializer ignores bool properties, de-serializing works fine.

Adding the following if clause to the method getPrimitiveReturnValueFromInvocation(NSInvocation * invocation)

} else if (!strcmp(returnType, @encode(bool))){
       bool result;
       [invocation getReturnValue:&result];
       resultValue = [NSNumber numberWithBool:result];
 }

Seems to resolve the issue

hasMany with ids

Hello,

I'm planning to implement a Relation to support array of ids.

{
  "id": 1,
  "category_ids" : [ 1, 2, 3, 4]
}

Any special consideration for an API like this. Any preference ?

Thanks!

Mapping to property of nested object

Hello,

I have few classes, like this:

@interface Pricing : NSObject
@property (nonatomic) NSString* locale;
@property (nonatomic) NSString* value;
@end

@implementation Pricing
@end


@interface Item : NSObject <EKMappingProtocol>
@property (nonatomic) Pricing* pricing;
@property (nonatomic) NSString* title;
@end

@implementation Item

+ (EKObjectMapping *)objectMapping {
    return [EKObjectMapping mappingForClass:self withBlock:^(EKObjectMapping *mapping) {
        [mapping mapKeyPath:@"title" toProperty:@"title"];
        [mapping mapKeyPath:@"pricing_locale" toProperty:@"pricing.locale"];
        [mapping mapKeyPath:@"pricing_value" toProperty:@"pricing.value"];
    }];
}

- (instancetype)init {
    self = [super init];
    if (self) {
        self.pricing = [[Pricing alloc] init];
    }
    return self;
}

@end

Then I do:

NSDictionary* representation = @{
                                     @"title":@"New item",
                                     @"pricing_locale":@"EN",
                                     @"pricing_value":@"0.99",
                                     };

Item* item = [[Item alloc] init];
[EKMapper fillObject:item fromExternalRepresentation:representation withMapping:[Item objectMapping]];

All ok -
item.title = @"New item"
item.pricing.locale = @"EN"
item.pricing.value = @"0.99"

But when I try to serialize item with this method:

[EKSerializer serializeObject:item withMapping:[Item objectMapping]]

I got exception:

*** Terminating app due to uncaught exception 'NSUnknownKeyException', reason: '[<Item 0x7af2d960> valueForUndefinedKey:]: this class is not key value coding-compliant for the key pricing.value.'

Maybe i doing something wrong?

Anyway if implement -valueForUndefinedKey: in Item class

- (id)valueForUndefinedKey:(NSString *)key {
    __block id value = nil;
    [[key componentsSeparatedByString:@"."] enumerateObjectsUsingBlock:^(id key, NSUInteger idx, BOOL *stop) {
        value = value?[value valueForKey:key]:[self valueForKey:key];
    }];
    return value;
}

All ok, but i don't like this way...

hasOneMapping fails to workaround the NSNull relationship in EKManagedObjectMapping

I tried to parse this JSON to NSManagedObjects:

[
        {
            id : "52f530d94c9abbcfcb000004",
            name : "Art / Culture",
            parent : null
        },
        {
            id : "52f530d94c9abbcfcb000001",
            name : "Music",
            parent : null
        }
]

With this mapping:

    [EKManagedObjectMapping mappingForEntityName:@"Category" withBlock:^(EKManagedObjectMapping *mapping) {
        [mapping mapFieldsFromArray:@[@"id",@"name"]];
        mapping.primaryKey = @"id";

        EKManagedObjectMapping *parentMapping = [EKManagedObjectMapping mappingForEntityName:@"Category" withBlock:^(EKManagedObjectMapping *objectMapping) {
            [objectMapping mapFieldsFromArray:@[@"id",@"name"]];
            objectMapping.primaryKey = @"id";
        }];
        [mapping hasOneMapping:parentMapping forKey:@"parent"];
    }];

But I kept getting error "The operation couldn’t be completed. (Cocoa error 1570.)". So, after hours of search I found out that the problem is really in EasyMapping itself!

@implementation EKMapper
+ (id)fillObject:(id)object fromExternalRepresentation:(NSDictionary *)externalRepresentation withMapping:(EKObjectMapping *)mapping {

Has:

if (externalRepresentation != (NSDictionary*)[NSNull null])

But:

+ (id)fillObject:(id)object fromExternalRepresentation:(NSDictionary *)externalRepresentation withMapping:(EKManagedObjectMapping *)mapping inManagedObjectContext:(NSManagedObjectContext *)moc {

Has incorrect if statement:

if (externalRepresentation) {

If you put "externalRepresentation != (NSDictionary*)[NSNull null]" to if statement, the bug will be fixed.

Mapping in one entity from different dictionary

Hi! Tanks for library. This is question, not issue
Can i get data from json dictionary and subdictionary for one entity?

i need one object

@Property (nonatomic, retain) NSNumber * id;
@Property (nonatomic, retain) NSString * name;
@Property (nonatomic, retain) NSNumber * parent_id;
@Property (nonatomic, retain) NSNumber * hobby_id;
@Property (nonatomic, retain) NSNumber * user_id;

i have this json

userHobby =     (
                {
            hobby =             {
                id = 3838;
                name = Xbox360;
                "parent_id" = 7;
            };
            "hobby_id" = 3838;
            "user_id" = 58;
        },
                {
            hobby =             {
                id = 1025;
                name = "Funk Music";
                "parent_id" = 1;
            };
            "hobby_id" = 1025;
            "user_id" = 58;
        },
                {
            hobby =             {
                id = 19855;
                name = Snowboarding;
                "parent_id" = 4;
            };
            "hobby_id" = 19855;
            "user_id" = 58;
        }
    );

New protocol pattern restricts mapping variations.

In version 0.6 when serialising or defining a hasOne or hasMany the pattern used to be that a mapping was provided via hasOneMapping etc.

In 0.7 this has been changed to an object class method to fetch the mapping.

I have a situation where I occasionally apply a different mapping in different use cases for the same object.
For example some nested objects contain partial objects, and in another case I have a legacy api that requires a slightly different mapping.

The new protocol pattern is now far more restrictive in that I can no longer implement either of these situations so have had to downgrade back to 0.6.

I wonder if there is perhaps some sort of context we can pass around so the the +(EKManagedObjectMapping *)objectMapping; can dynamically create the mapping ?

Or perhaps provide a mechanism to once again provide a mapping override in the hasOne mapping creation ?

Recursive mapping

For example, we have a tree of comments in json:

{
  "post_id" : 1312,
  "comments" : [
    { 
      "name" : "Bob",
      "message" : "Huston, we have a problem!",
      "sub_comments" : [
        {
          "name" : "Nick",
          "message" : "Oops!",
          "sub_comments" : [
            {
              "name" : "Bob",
              "message" : "It's a TRAP!",
              "sub_comments" : null
            }
          ]
        }
      ]
    },
    {
      "name" : "John",
      "message" : "Fire in a hole!!1",
      "sub_comments" : null
    }
  ]
}

Also, we have a mapping for comments:

+ (EKObjectMapping *)commentObjectMapping {
    return [EKObjectMapping mappingForClass:[CommentObject class]
                                   withBlock:^(EKObjectMapping *mapping) {
        [mapping mapKey:@"name" toField:@"name"];
        [mapping mapKey:@"message" toField:@"message"];
        [mapping hasManyMapping:mapping 
                         forKey:@"sub_comments" 
                       forField:@"subComments"];
    }];
}

As a result, an app crashed with a EXC_BAD_ACCESS. How to properly handle this case?

Add method to create dynamic mappings

Add a method like:

+ (EKObjectMapping *)dynamicMappingFor:(id)object;

on the EKObjectMapping class to generate dynamically a mapping for simple objects.

EKManagedObjectMapper 1570 errors.

I'm using v0.6.1.
I assigned a lot of hasOneMappings and a lot of hasManyMappings for my Core Data entities. But in many cases I get JSON without those properties. So my context fails to save with 1560 error (there are a lot of 1570 errors inside). It was telling me that it tried to set a nil value on object's property... So it turned out that there are 2 bugs in EKManagedObjectMapper.m:

if (value != (id)[NSNull null])

FIX:

if (value && value != (id)[NSNull null])

and

if (arrayToBeParsed != (id)[NSNull null])

FIX:

if (arrayToBeParsed && arrayToBeParsed != (id)[NSNull null])

Can't compile EasyMappingExample tests

Hi, it is very good library and I use it for communication with server in my application.

I've had this error:
/Users/andrewromanov/Documents/libs/EasyMapping/EasyMappingExample/EasyMappingExampleTests/EKSerializerSpec.m:9:9: 'Kiwi.h' file not found

NSNull with NSUInteger = crash

NSDictionary *d = @{@"supplier" : [NSNull null]};
Car *myCar = [[Car alloc] initWithProperty:d];
...
[mapping mapFieldsFromArray:@[@"supplier"]];
...
@Property (nonatomic, readwrite) NSUInteger supplier;

Issues with EKManagedObjectMapping for an NSManagedObject with properties also of type NSManagedObject

My API returns a JSON object called Ride with two child objects of type Location(PickupLocation and DropoffLocation). I want to map the ride object to an NSManagedObject using EasyMapping, but I'm running into trouble.

Here's what the json ride object looks like

{
  "Id": 1,
  "Username": "sample string 1",
  "UserProfileId": 2,
  "PickupLocation": {
    "Latitude": 1.1,
    "Longitude": 1.1,
    "StreetAddress": "sample string 1",
    "City": "sample string 2",
    "State": "sample string 3",
    "Zip": "sample string 4"
  },
  "DropoffLocation": {
    "Latitude": 1.1,
    "Longitude": 1.1,
    "StreetAddress": "sample string 1",
    "City": "sample string 2",
    "State": "sample string 3",
    "Zip": "sample string 4"
  },
  "NumberOfPassengers": 3,
  "ActualNumberOfPassengers": 4,
  "RequestTime": "2014-07-02T13:57:42.0503883-04:00",
  "Status": 5,
  "Eta": 1,
  "ShuttleId": 1,
  "AdaRequested": true,
  "DepartedTime": "2014-07-02T13:57:42.0503883-04:00",
  "PickupTime": "2014-07-02T13:57:42.0503883-04:00",
  "DropoffTime": "2014-07-02T13:57:42.0503883-04:00",
  "DeviceToken": "sample string 7",
  "DeviceType": "sample string 8",
  "DeviceVersion": "sample string 9"
}

The full Ride object is an NSManagedObject subclass and so are the two child Location Objects. Similarly to the example provided on the repo, I wrote a MappingProvider class. Here are the methods I wrote to return the EKManagedObjectMapping for both Ride and Location:

Ride

+ (EKManagedObjectMapping *)rideMapping
{
    return [EKManagedObjectMapping mappingForEntityName:@"Ride" withBlock:^(EKManagedObjectMapping *mapping) {
        [mapping mapFieldsFromDictionary:@
        {
            @"Id":@"ride_id",
            @"Username" : @"username",
            @"UserProfileId" : @"user_profile_id",
            @"NumberOfPassengers" : @"number_of_passengers",
            @"ActualNumberOfPassengers" : @"actual_number_of_passengers",
            @"Status" : @"ride_status",
            @"Eta" : @"eta",
            @"ShuttleId" : @"shuttle_id",
            @"AdaRequested" : @"ada_requested",
            @"DeviceToken" : @"device_token",
            @"DeviceType" : @"device_type",
            @"DeviceVersion" : @"device_version"

        }];
        [mapping  mapKey:@"RequestTime" toField:@"request_time" withDateFormat:dateFormat];
        [mapping  mapKey:@"DepartedTime" toField:@"departed_time" withDateFormat:dateFormat];
        [mapping  mapKey:@"PickupTime" toField:@"pick_up_time" withDateFormat:dateFormat];
        [mapping  mapKey:@"DropoffTime" toField:@"drop_off_time" withDateFormat:dateFormat];

        [mapping hasOneMapping:[self locationMapping] forKey:@"PickupLocation" forField:@"pick_up_location"];
        [mapping hasOneMapping:[self locationMapping] forKey:@"DropoffLocation" forField:@"drop_off_location"];

    }];
}

Location

+ (EKManagedObjectMapping *)locationMapping
{
    return [EKManagedObjectMapping mappingForEntityName:@"Location" withBlock:^(EKManagedObjectMapping *mapping) {
        [mapping mapFieldsFromDictionary:
         @{
           @"Latitude": @"latitude",
           @"Longitude" : @"longitude",
           @"StreetAddress" : @"street_address",
           @"City" : @"city",
           @"State" : @"state",
           @"Zip" : @"zip"
           }];
    }];
}

This seems to work well when I'm converting JSON into a ride object. My objects save to the core data store with no problems. However, when I go to fetch them, I get the following error:

-[Location initWithCoder:]: unrecognized selector sent to instance 0x1bdeb7a0

My guess is that when I perform the fetch on the ride object, EasyMapping is attempting to initialize the Location properties using NSCoding instead of CoreData. I looked a little further and discovered thathasOneMapping:forKey:forField: expects an EKObjectMapping instead of an EKManagedObjectMapping, so my guess is that my problem lies somewhere with that. If so, I'm confused how I set up the mappings for an object that has managed child objects. What is the best way to model this? Thanks for any help, and I apologize if this is the wrong place to ask this.

Mapping Managed Objects exchangeable with NSObject

Hi,

I have an object @interface MyManagedObject : NSManagedObject
it implements + objectMapping method and provides mapping

Can I map the objects with [EKMapper arrayOfObjectsFromExternalRepresentation:... withMapping:...]
as normal NSObjects, not as Managed objects for cases when I don't need to store them in CoreData? Or do I have to create a completely separate MyObject that is not a managed object for that and implement the same + objectMapping method?

Mapping relationships with just the other object's ID

How can i map if my JSON looks like this?

{
"id_reporte": 40,
"importante": "mas de lo mismo",
"mensaje": "igual",
"tarea": 0,
"estado_tarea": 1,
"fecha": "2014-10-21 10:29:08",
"id_nino": 38
"rango": 1
}

When id_nino belogns to an id of Nino object which already exists on my data base?
(i'm using core Data)

Does not work in Swift.

I am trying to follow your Swift examples, tried many ways, with EKMappingProtocol, with EKObjectModel and keep receiving "setValue:forUndefinedKey:]: this class is not key value coding-compliant for the key someRandomKey.'"

Any help appreciated

Undefined symbols for architecture armv7

Undefined symbols for architecture armv7:
  "_unw_step", referenced from:
      _kwCallerAddress in libPods-MyApp.a(KWSymbolicator.o)
  "_unw_getcontext", referenced from:
      _kwCallerAddress in libPods-MyApp.a(KWSymbolicator.o)
  "_unw_init_local", referenced from:
      _kwCallerAddress in libPods-MyApp.a(KWSymbolicator.o)
  "_unw_get_reg", referenced from:
      _kwCallerAddress in libPods-MyApp.a(KWSymbolicator.o)
ld: symbol(s) not found for architecture armv7
clang: error: linker command failed with exit code 1 (use -v to see invocation)

The solution is here.

Dividing array of objects with types after mapping

I have next JSON:

connections =     (
       {
            type = 1;
            value = "[email protected]";
        },
        {
            type = 1;
            value = "[email protected]";
        },
        {
            type = 2;
            value = 380503333334;
        }
    )
 

And I heve two properties:

@property (nonatomic, strong) NSMutableArray *phones; // type = 2
@property (nonatomic, strong) NSMutableArray *emails; // type = 1

The best way I have found to map them was:

[mapping mapKey:@"connections" toField:@"phones" withValueBlock:^id (NSString *key, id value) {
    NSArray *listOfJSONs = (NSArray *)value;
    NSMutableArray *connections = [NSMutableArray arrayWithCapacity:listOfJSONs.count];
    for (NSDictionary *JSON in listOfJSONs) {
        Connection *connection = [Connection objectWithJSON:JSON];
        [connections addObject:connection];
    }
    
    NSPredicate *phonesQuery = [NSPredicate predicateWithFormat:@"type == %i", CONNECTION_TYPE_PHONE];
    return [[connections filteredArrayUsingPredicate:phonesQuery] mutableCopy];
}];
[mapping @"connections" toField:@"emails" withValueBlock:^id (NSString *key, id value) {
    NSArray *listOfJSONs = (NSArray *)value;
    NSMutableArray *connections = [NSMutableArray arrayWithCapacity:listOfJSONs.count];
    for (NSDictionary *JSON in listOfJSONs) {
        Connection *connection = [Connection objectWithJSON:JSON];
        [connections addObject:connection];
    }
    
    NSPredicate *emailsQuery = [NSPredicate predicateWithFormat:@"type == %i", CONNECTION_TYPE_EMAIL];
    return [[connections filteredArrayUsingPredicate:emailsQuery] mutableCopy];
}];

In this way I need parse connections twice. Could you help me to find better solution for such kind of JSONes?

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.