2013-05-07 4 views
1

J'ai un NSPersistentDocument avec un modèle de données de base donné, etc.Comment précharger des données à partir des données de base dans un document NSPersistentDocument?

J'ai un fichier, créé par ce document, Répétons le son preload.xml. Il "contient" plusieurs NSManagedObject s.

Je voudrais charger ces objets dans tous mes nouveaux documents, de sorte que lorsque je crée un nouveau document, le nouveau document "a" automatiquement les objets "vivant" dans preload.xml. Jusqu'à présent, voici ce que je faisais:

  • Je copié preload.xml dans mon projet.

  • Dans la méthode initWithType:error: (la méthode appelée lorsqu'un nouveau document est créé), avoir le code suivant:

    NSURL *preloadURL = [NSURL fileURLWithPath:[[NSBundle mainBundle] 
                  pathForResource:@"preload" 
                  ofType:@"xml"]]; 
    NSError* err = nil; 
    
    [self readFromURL:preloadURL 
          ofType:@"xml" 
          error:&err] ; 
    

Cela ne fonctionne pas parce que, lorsque je tente ensuite de sauver ma document à, disons myNewDoc.xml, ce fichier est vide mais toutes mes nouvelles données sont enregistrées à preload.xml. Je me demande si je dois créer un nouveau store ou context ou storeCoordinator ou autre chose. Je n'ai jamais traité avec de tels objets puisque j'ai toujours utilisé NSPersistentDocument.

+0

Est-ce que vous substituez 'readFromURL: ofType : erreur: '? Si oui, à quoi ressemble votre version? –

+0

Oui, je remplace 'readFromURL' mais cela ne fonctionne pas. J'ai fait quelque chose d'autre, depuis: créer un nouveau 'store' (associé à mon preload.xml), un nouveau' storeCoord' et un nouveau 'MOC'. Ensuite, j'ai eu un clone mes objets entre les deux MOC, ce qui n'est pas si génial ... Mais ça a l'air de marcher. – Colas

+0

Eh bien, il semble que le problème original soit en quelque sorte lié à votre code 'readFromURL: ofType: error:', et puisque vous n'avez pas inclus cela, il est difficile de dire ce qui pourrait ne pas fonctionner. –

Répondre

1

Obtenir les objets enregistrés:

NSPersistentStoreCoordinator * newPersStoreCoord ; 
    newPersStoreCoord = [[NSPersistentStoreCoordinator alloc] initWithManagedObjectModel:theDoc.managedObjectModel] ; 

    NSString * path = [[NSBundle mainBundle] pathForResource:@"preload" 
                 ofType:@"xml"]; 
    NSURL *preloadURL = [NSURL fileURLWithPath:path]; 



    [newPersStoreCoord addPersistentStoreWithType:NSBinaryStoreType 
            configuration:nil 
               URL:preloadURL 
              options:nil 
              error:NULL] ; 

    NSManagedObjectContext * auxMOC = [[NSManagedObjectContext alloc] init] ; 
    [auxMOC setPersistentStoreCoordinator:newPersStoreCoord] ; 

les copier sur votre "vie" MOC

[self loadPreloadedDataFromTheMOC:auxMOC 
          toTheMOC:theDoc.managedObjectContext 
          forTheDoc:theDoc] ; 

avec l'aide des techniques de clonage

- (NSManagedObject *)cloneInContext:(NSManagedObjectContext *)context 
        withCopiedCache:(NSMutableDictionary *)alreadyCopied 
        exludeEntities:(NSArray *)namesOfEntitiesToExclude 
        excludeAttributes:(NSArray *)namesOfAttributesToExclude 
{ 
    NSString *entityName = [[self entity] name]; 

    if ([namesOfEntitiesToExclude containsObject:entityName]) 
    { 
     return nil; 
    } 

    NSManagedObject *cloned = [alreadyCopied objectForKey:[self objectID]]; 
    if (cloned != nil) 
    { 
     return cloned; 
    } 


    //create new object in data store 
    cloned = [NSEntityDescription insertNewObjectForEntityForName:entityName 
              inManagedObjectContext:context]; 
    [alreadyCopied setObject:cloned 
         forKey:[self objectID]]; 

    //loop through all attributes and assign then to the clone 
    NSDictionary *attributes = [[NSEntityDescription entityForName:entityName 
              inManagedObjectContext:context] attributesByName]; 


    for (NSString *attr in attributes) 
    { 
     if (![namesOfAttributesToExclude containsObject:attr]) 
     { 
      [cloned setValue:[self valueForKey:attr] forKey:attr]; 
     } 
    } 

    //Loop through all relationships, and clone them. 
    NSDictionary *relationships = [[NSEntityDescription entityForName:entityName 
               inManagedObjectContext:context] relationshipsByName]; 



    for (NSString *relName in [relationships allKeys]) 
    { 
     NSRelationshipDescription *rel = [relationships objectForKey:relName]; 

     NSString *keyName = rel.name; 

     if ([rel isToMany]) 
     { 
      id sourceSet ; 
      id clonedSet ; 

      /* 
      On gère selon que la relation est ordonnée ou non 
      */ 
      if (![rel isOrdered]) 
      { 
       //get a set of all objects in the relationship 
       sourceSet = [self mutableSetValueForKey:keyName]; 
       clonedSet = [cloned mutableSetValueForKey:keyName]; 
      } 
      else 
      { 
       sourceSet = [self mutableOrderedSetValueForKey:keyName]; 
       clonedSet = [cloned mutableOrderedSetValueForKey:keyName]; 
      } 

      NSEnumerator *e = [sourceSet objectEnumerator]; 
      NSManagedObject *relatedObject; 

      while (relatedObject = [e nextObject]) 
      { 
       //Clone it, and add clone to set 
       NSManagedObject *clonedRelatedObject = [relatedObject cloneInContext:context 
                    withCopiedCache:alreadyCopied 
                     exludeEntities:namesOfEntitiesToExclude 
                    excludeAttributes:namesOfAttributesToExclude]; 
       if (clonedRelatedObject) 
       { 
        [clonedSet addObject:clonedRelatedObject]; 
       } 
      } 
     } 
     else 
     { 
      NSManagedObject *relatedObject = [self valueForKey:keyName]; 
      if (relatedObject != nil) 
      { 
       NSManagedObject *clonedRelatedObject = [relatedObject cloneInContext:context 
                    withCopiedCache:alreadyCopied 
                     exludeEntities:namesOfEntitiesToExclude 
                    excludeAttributes:namesOfAttributesToExclude]; 
       if (clonedRelatedObject) 
       { 
        [cloned setValue:clonedRelatedObject forKey:keyName]; 
       } 
      } 
     } 
    } 

    return cloned; 
} 
Questions connexes