NSManagedObjectID в NSData - PullRequest
       13

NSManagedObjectID в NSData

13 голосов
/ 05 февраля 2009

Я нашел этот замечательный NSManagedObjectID. Это было бы очень хорошо для ссылки на Entity / NSManagedObject / NSEntityDescription, верно?
Давайте получим идентификатор от сущности:

NSEntityDescription *entity = [self newEntity];     
NSManagedObjectID *objID = [entity objectID];

Итак ... есть идеи, как получить это objID в строку? Или лучше: NSData. На самом деле что-то, чтобы иметь возможность сохранить его в NSUserDefaults. ;-)

Кстати: NSFetchRequest не хочет работать в моем случае. Я использую модифицированную версию этого примера: ответ на старый вопрос .

Ответы [ 6 ]

38 голосов
/ 05 февраля 2009

Чтобы получить архивированный URI, соответствующий NSManagedObject 's objectID:

NSManagedObject* myMO;
...
NSURL *uri = [[myMO objectID] URIRepresentation];
NSData *uriData = [NSKeyedArchiver archivedDataWithRootObject:uri];

Чтобы вернуться к экземпляру исходного управляемого объекта, вам нужен стек CoreData с постоянным хранилищем, в котором этот экземпляр уже добавлен к NSPersistentStoreCoordinator. Тогда:

NSData *uriData;
NSPersistentStoreCoordinator *psc;
NSManagedObjectContext *moc; //with moc.persistentStoreCoordinator = psc.
...
NSURL *uri = [NSKeyedUnarchiver unarchiveObjectWithData:uriData];
NSManagedObjectID *moID = [psc managedObjectIDForURIRepresentation:uri];
NSManagedObject *myMO = [moc objectWithID:moID];
5 голосов
/ 05 февраля 2009

Из NSManagedObjectID документация :

Идентификаторы объектов могут быть преобразованы в Представление URI, которое может быть заархивирован и воссоздан позже для ссылки вернуться к заданному объекту (используя managedObjectIDForURIRepresentation: (NSPersistentStoreCoordinator) и objectWithID: (NSManagedObjectContext). Например, последняя выбранная группа в приложение может быть сохранено в пользователь по умолчанию через группу ID объекта. Вы также можете использовать объект ID URI представлений для хранения «слабых» отношения через постоянные магазины (где жесткое соединение невозможно).

Просто превратите его в URL, затем превратите его в строку или данные.

3 голосов
/ 29 декабря 2013

Вот самый чистый и кратчайший способ, который я нашел, чтобы сделать это в настоящее время, используя методы setURL и getURL, добавленные в 4.0, чтобы избежать дополнительных вызовов NSKeyedUnarchiver и NSKeyedArchiver:

сеттер:

 + (void)storeSomeObjectId:(NSManagedObjectID *)objectId
 {
     [[NSUserDefaults standardUserDefaults] setURL:[objectId URIRepresentation] 
                                            forKey:@"someObjectIdKey"];
     [[NSUserDefaults standardUserDefaults] synchronize];
 }

Getter:

 + (SomeManagedObject *)getObjectByStoredId
 {
     NSURL *uri = [[NSUserDefaults standardUserDefaults] URLForKey:@"someObjectIdKey"];
     NSManagedObjectID *objectId = [self.persistentStoreCoordinator managedObjectIDForURIRepresentation:uri];
     SomeManagedObject *object = [self.managedObjectContext objectWithID:objectId];
 }
3 голосов
/ 07 октября 2009

Вам не нужно преобразовывать NSURL в строку NSString перед архивированием. Просто заархивируйте NSURL.

Редактировать. Недавно я узнал, что идентификатор объекта может измениться, например, после миграции. Поэтому кажется не очень хорошей идеей сохранить идентификатор на диск, ожидая, что он сможет ссылаться на объект позже.

3 голосов
/ 05 февраля 2009

Вы смотрели на URIRпредставление ? Преобразовать NSURL в NSString легко, а в NSData.

0 голосов
/ 05 апреля 2013

Как сказал @preston, не сохраняйте objectID на диск, вместо этого:

  1. Создайте новый атрибут в вашей сущности с именем "id"
  2. Создайте новый атрибут в родительской сущности вашей сущности с именем «myEntitysMaxId»
  3. Переопределить родительскую реализацию ваших сущностей "addNewMyEntityObject:"
  4. Там увеличьте «myEntitysMaxId» и установите это значение в качестве новых сущностей «id»
  5. Делайте как обычно, когда выбираете объект на основе его атрибутов!

Намного чище и лучше!

...