iosrestkitrestkit-0.20

RestKit one to many relationship inverse mapping


I'm using RestKit to map JSON API to iOS objects

+ (RKObjectMapping *)addressMapping
{
    RKObjectMapping *mapping = [RKObjectMapping mappingForClass:[Address class]];

    [mapping addAttributeMappingsFromDictionary:@{
                                                  @"id": @"idAddress",
                                                  @"id_city": @"idCity",
                                                  @"id_country": @"idCountry"
                                                  }];

    return mapping;
}

+ (RKObjectMapping *)userMapping
{
    RKObjectMapping *mapping = [RKObjectMapping mappingForClass:[User class]];

    [mapping addAttributeMappingsFromDictionary:@{
                                                  @"id": @"idUser",
                                                  @"email": @"email",
                                                  }];

    [mapping addPropertyMapping:[RKRelationshipMapping relationshipMappingFromKeyPath:@"address" toKeyPath:@"address" withMapping:[self addressMapping]]];
    [mapping addPropertyMapping:[RKRelationshipMapping relationshipMappingFromKeyPath:@"branch_addresses" toKeyPath:@"branchAddresses" withMapping:[self addressMapping]]];

    return mapping;
}

When I'm getting data from API, they're correctly mapped to classes:

RKResponseDescriptor *responseDescriptorGet =
    [RKResponseDescriptor responseDescriptorWithMapping:[RestMappingProvider userMapping]
                                                 method:RKRequestMethodGET
                                            pathPattern:@"/api/user/user"
                                                keyPath:@"data"
                                            statusCodes:RKStatusCodeIndexSetForClass(RKStatusCodeClassSuccessful)];

However when I'm updating data, the one to many relationship (branch_addresses) is not mapped correctly:

RKRequestDescriptor *requestDescriptor =
    [RKRequestDescriptor requestDescriptorWithMapping:[[RestMappingProvider userMapping] inverseMapping]
                                          objectClass:[User class]
                                          rootKeyPath:nil
                                               method:RKRequestMethodPUT];

Data received by the server:

[id] => 123
[email] => test@test.com
[address] => Array
    (
        [id] => 3
        [id_city] => 1
        [id_country] => 1
    )
[branch_addresses] => Array
    (
        [0] => Array
            (
                [id] => 4
            )

        [1] => Array
            (
                [id_city] => 1
            )

        [2] => Array
            (
                [id_country] => 1
            )
    )

What data should looks like on the server:

[id] => 123
[email] => test@test.com
[address] => Array
    (
        [id] => 3
        [id_city] => 1
        [id_country] => 1
    )
[branch_addresses] => Array
    (
        [0] => Array
            (
            [id] => 4
            [id_city] => 1
            [id_country] => 1
            )
    )

Content of php://input on server side (raw data):

id=123&email=test%40test.com&address[id]=3&address[id_city]=1&address[id_country]=1&branch_addresses[][id]=4&branch_addresses[][id_city]=1&branch_addresses[][id_country]=2&branch_addresses[][id]=6&branch_addresses[][id_city]=1&branch_addresses[][id_country]=1

Solution

  • Not all forms of data transmission are equally expressive. It seems you're sending query parameters instead of JSON, or at least a form encoded set of data. You need to set the default request mime type so restkit knows you want to send JSON and it converts to the required format.