محاولة غير قانونية لإنشاء علاقة "xyz" بين الأشياء في سياقات مختلفة
-
20-09-2019 - |
سؤال
أنا أستخدم Apple's CoreDataBooks
عينة من التطبيق كأساس لسحب البيانات إلى سياق كائن مُدار ثانوي في الخلفية ، ثم دمج تلك البيانات في سياق الكائن الرئيسي المدار.
البيانات التي أسحبها هي Book
كيان مع علاقة مع Owner
الكيان (يسمى "المالك"). ال Owner
الكيان لديه علاقة إلى حد ما مع Book
(تسمى "الكتب").
بياناتي هي مستند XML للنموذج:
<Owner>
<Name>alexpreynolds</Name>
<ID>123456</ID>
</Owner>
<Books>
<Book>Book One</Book>
<Book>Book Two</Book>
...
<Book>Book N</Book>
</Books>
Book One
عبر Book N
ترتبط بواحد Owner
("alexpreynolds, 123456"
).
أنا أقوم بتحليل هذا في Owner
مثيل و NSMutableSet
صنع من Book
حالات.
عندما أحاول حفظ المرة الأولى ، فإنه يحفظ بشكل جيد وتظهر البيانات المدمجة في عرض الجدول.
في الثانية الحفظ ، ومع ذلك ، عندما يحتوي محتوى XML على كتاب جديد ، فإنه لا يعمل.
هذا ما يحدث:
أحاول بعد ذلك التحميل في مستند XML يحتوي على جديد Book
ليس بالفعل في سياق الكائن الرئيسي المدار. الجديد Book
يستخدم نفس الشيء Owner
كما يرتبط الآخر Book
س.
لدي إجراءات تختار هذا الفريد Owner
كائن مُدار (الذي لدي بالفعل في سياق الكائن الرئيسي المدار) والفريد من نوعه Book
إنه ليس وجدت في MOC الأولية.
من هذا ، أقوم بإنشاء جديد Book
كائن في MOC الثانوية ، وقمت بتعيينه "owner
"العلاقة للإشارة إلى الفريدة Owner
لقد وجدت في MOC الأساسي.
عندما أحفظ ، أحصل على الخطأ التالي:
*** Terminating app due to uncaught
exception 'NSInvalidArgumentException',
reason: 'Illegal attempt to establish a
relationship 'owner' between objects in
different contexts
(source = <Book: 0x7803590>
(entity: Book; id: 0x7802ae0 <x-coredata:///
Book/t527F06B2-3EB5-47CF-9A29-985B0D3758862>
; data: {
creationDate = 2009-10-12 06:01:53 -0700;
name = nil;
nameInitial = nil;
operations = (
);
owner = nil;
type = 0;
}) ,
destination = <Owner: 0x78020a0> (entity:
Owner; id: 0x3a56f80 <x-coredata://043AF2F0-1AD0-
4078-A5E8-E9D7071D67D1/Owner/p1> ; data: {
books = "<relationship fault: 0x7801bf0 'books'>";
displayName = alexpreynolds;
ownerID = 123456;
}))'
كيف أقوم بإنشاء جديد Book
الكيان في MOC الثانوية ، حتى لا يزال بإمكاني ربطه بموجب موجود مسبقًا Owner
في MOC الأساسي؟
المحلول
لا يمكن أن يكون لديك علاقات بين الكائنات في سياقات الكائنات المدارة المختلفة. لذا فإن إحدى طرق الالتفاف حول جلب الكائن إلى سياق الكائن المدار.
علي سبيل المثال:
NSManagedObject *book = // get a book in one MOC
NSManagedObject *owner = // get an owner in a different MOC
[[owner mutableSetValueForKey:@"books"] addObject:[owner.managedObjectContext objectWithID:[book objectID]]];
إذن ما تفعله هو في الواقع جلب Book
في نفس سياق الكائن المدار مع owner
. ضع في اعتبارك أن هذا ممكن فقط إذا book
تم حفظه بالفعل. سيبحث سياق الكائن المدار عن الكائن في المتجر الثابت ، لذلك يجب حفظه أولاً.
نصائح أخرى
واجهت نفس المشكلة وقد ساعدتني هذه الجملة على حل الخطأ.
لا يمكن أن يكون لديك علاقات بين الكائنات في سياقات الكائنات المدارة المختلفة. لذا فإن إحدى طرق الالتفاف حول جلب الكائن إلى سياق الكائن المدار.
إليك الكود الخاص بي (استبدلت المتغيرات لجعله يعمل من أجلك):
// Have the owner object and get the managedObjectContext
Owner *owner = [[DataFunctions alloc] getCurrentOwner];
NSManagedObjectContext *context = [owner managedObjectContext];
// Create a book and use the manageObjectContext of owner
Book *book = [NSEntityDescription insertNewObjectForEntityForName:@"Book" inManagedObjectContext:context];
[newQuote setValue: "Book Title" forKey:@"title"];
[newQuote setOwner:owner];
آمل أن يساعد هذا :)
هنا ، تحاول إنشاء علاقة بين كائنين يتم جلبهما/تم إنشاؤه مع سياق مختلف. لن تسمح لك البيانات الأساسية بإنشاء مثل هذه العلاقات. لتحقيق ذلك ، يجب أن تجلب الكائن الثاني (تحاول إقامة علاقة مع) مع سياق الكائن الأول مع ObjectID. الآن يجب أن تكون قادرًا على إنشاء علاقة بين هذين الكائنين. علي سبيل المثال:
MagicalRecord.saveWithBlock({[unowned self] (localContext: NSManagedObjectContext!) in
let user = User.MR_createEntityInContext(localContext)!
.....
.....
}) //here local context stores data on end of block itself
MagicalRecord.saveWithBlock({[unowned self] (localContext: NSManagedObjectContext!) in
let address = Address.MR_createEntityInContext(localContext)!
.....
.....
let user = localContext.objectWithID(self.user!.objectID) as! User
user.address = address
})
ارجوا ان يساعدك هذا!
كما يقول الخطأ ، لا يُسمح لك بوجود علاقة في كائن بيانات أساسي يتم تعيين قيمته على كائن آخر محتجز في سياق مختلف. إحدى الطرق التي يمكنك من خلالها الالتفاف على هذا الانتظار حتى بعد حفظ الكائن الجديد ودمجه مرة أخرى في السياق الأساسي ، ثم قم بتعيين owner
العلاقة حسب الاقتضاء (نظرًا لأن كلا الكائنين الآن في نفس السياق ، فلا توجد مشكلة في ذلك).
book *book = [mainContext ........] //Get book from default context
NSManagedObjectID *objectId = [book objectID];
Book *tmpBook = [tmpContext objectWithID:objectId]; //Now book has the legal relationship
نسخة سريعة ...
context.insert(objectFromOtherContext)