Search code examples
ioscore-dataios7

Retrieve operation unexpected behaviour in iOS CoreData


I am storing the data in iOS and trying to retrieve it. For that i am using below function :

        NSManagedObjectContext *managedObjectContext = [DatabaseOperation managedObjectContext];
        NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] initWithEntityName:CODE_SEARCH_ENTITY];
        NSMutableArray *datasAA = [[managedObjectContext executeFetchRequest:fetchRequest error:nil] mutableCopy];
        NSMutableArray *retrievedData = datasAA;
        NSLog(@"Dictionary Data: %@",retrievedData);

First time i am getting below response :

"<NSManagedObject: 0x7d668660> (entity: xyx; id: 0x7d668570 <x-coredata://48CFFB0A-DF7C-468B-A134-87BACFEA95CC/CodeSearchTable/p52> ; data: {\n    codeFoils = 12;\n    codeHospitalPrice = 6786;\n    codeId = 88;\n    codeMaxRetail = 9240;\n    codeNeedleDesc = \"1/2 Circle Round Body Blunt\";\n    codeNeedleDimen = \"44 MM\";\n    codeNid = NW9367;\n    codeSize = 1;\n    sutureTypeLength = \"PDS II Monofilament (Voilet) 150 CM Loop\";\n})",
"<NSManagedObject: 0x7d668770> (entity: xyx; id: 0x7d6684b0 <x-coredata://48CFFB0A-DF7C-468B-A134-87BACFEA95CC/CodeSearchTable/p53> ; data: {\n    codeFoils = 12;\n    codeHospitalPrice = 5149;\n    codeId = 88;\n    codeMaxRetail = 6960;\n    codeNeedleDesc = \"1/2 Circle Round Body (Heavy)\";\n    codeNeedleDimen = \"40 MM\";\n    codeNid = NW9371;\n    codeSize = \"1/0\";\n    sutureTypeLength = \"PDS II Monofilament (Voilet) 90 CM\";\n})",

but next time when i am running the same giving me below result:

"<NSManagedObject: 0x78616510> (entity: xyz; id: 0x78760110 <x-coredata://B8C411F0-5C73-413B-8709-B7F805B6E413/CodeSearchTable/p611> ; data: <fault>)",
"<NSManagedObject: 0x78616550> (entity: xyz; id: 0x78760120 <x-coredata://B8C411F0-5C73-413B-8709-B7F805B6E413/CodeSearchTable/p612> ; data: <fault>)",

Please explain me what wrong i am doing over here. Thanks in advance.


Solution

  • There is not necessarily a problem with some Core Data objects being in "fault" state.

    Have a look at this document, which explains it all.

    In short:

    • faulting is a mechanism to improve performance (memory usage);

    • the mechanism should work transparently:

      • an object can be faulted (by the SDK) to reduce memory usage, then

      • relived when it is needed, e.g., when accessing an attribute.

    • there are exceptions (which leads to undesired behaviour):

      • an object is faulted due to it being deleted; in that case, trying and accessing it, will make your app crash; you should check the inverse relationship and think about the nullify or cascade delete rule;

      • your implementation files (in Obj-C) do no declare the attribute as @dynamic, rather they use @synthesize.

    What happens in your case is likely the following:

    • on the first fetch the objects are retrieved and cached (in Core Data cache);
    • for some reason (hopefully, not because you are deleting them!) the objects in the cache are faulted to free some memory for your app;

    If this is the scenario, there is nothing wrong with faulting.

    Please, try and add the following statements at the end of your method to check whether the the objects can be brought back into memory after faulting:

    NSLog(@"Object: %@", [retrievedData firstObject]);
    NSLog(@"Object attribute: %@", [[retrievedData firstObject] valueForKey:@"codeFoils"]);