Note that there are some explanatory texts on larger screens.

plurals
  1. POCore Data relationship delete rule - Nullify + Cascade
    primarykey
    data
    text
    <p>Entities:</p> <ul> <li>Video</li> <li>Playlist Item</li> <li>Playlist</li> </ul> <p>Relationships:</p> <ul> <li>Video is optional to-many to Playlist Item and the delete rule is nullify</li> <li>Playlist is to-many to at least one Playlist Items and the delete rule is nullify</li> <li>Playlist Item is required to-one for Video and the delete rule is nullify</li> <li>Playlist Item is required to-one for Playlist and the delete rule is nullify</li> </ul> <p>In the Playlist entity, I have not exposed the playlistItem relationship / set. Instead I have a transient undefined attribute called "videos," which is an array of Video entities generated by sorting the set of Playlist Items. There is not a relationship between Playlist and Video entities.</p> <p>I'm having problems when saving a modified Playlist instance in the Managed Object Context.</p> <p><em>From playlist.m (NSManagedObject subclass):</em></p> <pre><code>- (BOOL)validatePlaylistItems:(NSSet **)playlistItems error:(NSError **)outError { NSArray *currentVideos = [self videos]; NSArray *persistedVideos = [self videosFromPlaylistItems]; if ([currentVideos isEqual:persistedVideos]) { return YES; } NSManagedObjectContext *context = [self managedObjectContext]; for (FHPlaylistItem *pi in *playlistItems) { [context deleteObject:pi]; } NSArray *videos = [self primitiveVideos]; NSUInteger count = [videos count]; for (int i = 0; i &lt; count; i++) { FHPlaylistItem *pi = [FHPlaylistItem playlistItemWithVideo:[videos objectAtIndex:i] forIndex:i insertIntoManagedObjectContext:[self managedObjectContext]]; [self addPlaylistItemsObject:pi]; [pi setPlaylist:self]; } return YES; } </code></pre> <p>What I'm trying to accomplish here is only update the set of Playlist Items when the MOC needs to save, as you can see the operation is expensive - O(N * 2). During the first run of the app, the MOC saves just fine. However, subsequent changes to the videos attribute yields in Core Data spewing a bunch of errors:</p> <pre><code>Core Data: annotation: repairing missing delete propagation for to-many relationship playlistItems on object &lt;FHPlaylist: 0x6c27eb0&gt; (entity: Playlist; id: 0x6c26d40 &lt;x-coredata://BCB69D8E-8393-4A2A-AF5D-0AA1872CE2B4/Playlist/p19&gt; ; data: { accountID = 0; lastFetched = "2012-03-31 20:05:08 +0000"; name = Featured; playlistID = 1441335931001; playlistItems = ( "0x6c34be0 &lt;x-coredata:///PlaylistItem/t9EAFBC87-5E16-4053-984F-881CCD9C1F0B2&gt;", "0x6c34320 &lt;x-coredata://BCB69D8E-8393-4A2A-AF5D-0AA1872CE2B4/PlaylistItem/p16&gt;", "0x6c310c0 &lt;x-coredata:///PlaylistItem/t9EAFBC87-5E16-4053-984F-881CCD9C1F0B3&gt;", "0x6c35570 &lt;x-coredata:///PlaylistItem/t9EAFBC87-5E16-4053-984F-881CCD9C1F0B5&gt;", "0x6c34ca0 &lt;x-coredata:///PlaylistItem/t9EAFBC87-5E16-4053-984F-881CCD9C1F0B6&gt;", "0x6c34310 &lt;x-coredata://BCB69D8E-8393-4A2A-AF5D-0AA1872CE2B4/PlaylistItem/p8&gt;", "0x6c28a90 &lt;x-coredata:///PlaylistItem/t9EAFBC87-5E16-4053-984F-881CCD9C1F0B4&gt;", "0x6c34350 &lt;x-coredata://BCB69D8E-8393-4A2A-AF5D-0AA1872CE2B4/PlaylistItem/p29&gt;", "0x6c34220 &lt;x-coredata://BCB69D8E-8393-4A2A-AF5D-0AA1872CE2B4/PlaylistItem/p2&gt;", "0x6c34330 &lt;x-coredata://BCB69D8E-8393-4A2A-AF5D-0AA1872CE2B4/PlaylistItem/p20&gt;", "(...and 1 more...)" ); playlistType = 0; referenceID = OKFFeaturedPlaylist; shortDescrip = "This is so descriptive! OMG!"; thumbnailURL = nil; videos = "(...not nil..)"; }) with bad fault 0x6c34320 &lt;x-coredata://BCB69D8E-8393-4A2A-AF5D-0AA1872CE2B4/PlaylistItem/p16&gt; Core Data: annotation: repairing missing delete propagation for to-many relationship playlistItems on object &lt;FHPlaylist: 0x6c27eb0&gt; (entity: Playlist; id: 0x6c26d40 &lt;x-coredata://BCB69D8E-8393-4A2A-AF5D-0AA1872CE2B4/Playlist/p19&gt; ; data: { accountID = 0; lastFetched = "2012-03-31 20:05:08 +0000"; name = Featured; playlistID = 1441335931001; playlistItems = ( "0x6c34be0 &lt;x-coredata:///PlaylistItem/t9EAFBC87-5E16-4053-984F-881CCD9C1F0B2&gt;", "0x6c310c0 &lt;x-coredata:///PlaylistItem/t9EAFBC87-5E16-4053-984F-881CCD9C1F0B3&gt;", "0x6c35570 &lt;x-coredata:///PlaylistItem/t9EAFBC87-5E16-4053-984F-881CCD9C1F0B5&gt;", "0x6c34ca0 &lt;x-coredata:///PlaylistItem/t9EAFBC87-5E16-4053-984F-881CCD9C1F0B6&gt;", "0x6c34310 &lt;x-coredata://BCB69D8E-8393-4A2A-AF5D-0AA1872CE2B4/PlaylistItem/p8&gt;", "0x6c28a90 &lt;x-coredata:///PlaylistItem/t9EAFBC87-5E16-4053-984F-881CCD9C1F0B4&gt;", "0x6c34350 &lt;x-coredata://BCB69D8E-8393-4A2A-AF5D-0AA1872CE2B4/PlaylistItem/p29&gt;", "0x6c34220 &lt;x-coredata://BCB69D8E-8393-4A2A-AF5D-0AA1872CE2B4/PlaylistItem/p2&gt;", "0x6c34330 &lt;x-coredata://BCB69D8E-8393-4A2A-AF5D-0AA1872CE2B4/PlaylistItem/p20&gt;", "0x6c34340 &lt;x-coredata://BCB69D8E-8393-4A2A-AF5D-0AA1872CE2B4/PlaylistItem/p27&gt;" ); playlistType = 0; referenceID = OKFFeaturedPlaylist; shortDescrip = "This is so descriptive! OMG!"; thumbnailURL = nil; videos = "(...not nil..)"; }) with bad fault 0x6c34310 &lt;x-coredata://BCB69D8E-8393-4A2A-AF5D-0AA1872CE2B4/PlaylistItem/p8&gt; Etc. Etc. Etc. </code></pre> <p>It seems to be the problem lies with the delete rule. The complaint is with a "missing delete propagation," so it seems nullify is the wrong choice. But, why is it wrong? This doesn't make sense to me. The wording of the cascade delete rule in <a href="https://developer.apple.com/library/mac/documentation/Cocoa/Conceptual/CoreData/Articles/cdRelationships.html#//apple_ref/doc/uid/TP40001857-SW1" rel="noreferrer">Apple's Core Data Programming Guide</a> makes it seem like I'm going to delete the Video and Playlist objects if I set Playlist Item's delete rule to cascade.</p> <blockquote> <p>Cascade - Delete the objects at the destination of the relationship</p> </blockquote> <p><strike>Furthermore, if I set the relationship from Playlist Item to video &amp; playlist to nil in the fast enumeration loop, Core Data doesn't complain about having to repair the missing delete propagation.</p> <pre><code>for (FHPlaylistItem *pi in *playlistItems) { [pi setVideo:nil]; [pi setPlaylist:nil]; [context deleteObject:pi]; } </code></pre> <p></strike> EDIT: Nope, nil'ing the relationships manually didn't work in all situations. (Maybe no surprise?)</p>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload