NSFileVersion: resolve conflict by copying file

252 views Asked by At

I have NSFilePresenter for the entire Documents folder. I used to put files in iCloud container and if files were created at the same time on multiple devices, they were automatically renamed by iCloud. At the same time presentedSubitemAtURL:(didMoveToURL: would notify me that certain file created on certain device was renamed. It's important because it's the only way I know that files are being automatically moved by iCloud.

However, now I started resolving conflicts myself and implemented - (void)presentedSubitemAtURL:(NSURL *)url didGainVersion:(NSFileVersion *)version because I don't always want iCloud to simply rename files, sometimes I want to write in-place.

What is the proper way of separating conflicting versions of the same file onto two files in the same fashion as iCloud does? So if both devices wrote file.txt at the same time, I want one of files to be moved to file 2.txt.

So far I have the resolution that picks up the most recent version of file.

- (void)presentedSubitemAtURL:(NSURL *)url didGainVersion:(NSFileVersion *)version {
    // bail if no conflicts
    if(!version.isConflict) {
        return;
    }

    // get all conflicts
    NSArray* conflictVersions = [NSFileVersion unresolvedConflictVersionsOfItemAtURL:url];
    NSSortDescriptor *sortDescriptor = [NSSortDescriptor sortDescriptorWithKey:NSStringFromSelector(@selector(modificationDate)) ascending:NO];

    // sort by recency
    conflictVersions = [conflictVersions sortedArrayUsingDescriptors:@[ sortDescriptor ]];

    // pick the most recent version
    NSFileVersion *recentVersion = conflictVersions.firstObject;

    // replace current item with the most recent version
    NSError *replaceError;
    if(![recentVersion replaceItemAtURL:url options:0 error:&replaceError]) {
        return;
    }

    // mark all conflicts as resolved
    for(NSFileVersion* fileVersion in conflictVersions) {
        fileVersion.resolved = YES;
    }

    // clean up other versions
    NSError *removeError;
    if(![NSFileVersion removeOtherVersionsOfItemAtURL:url error:&removeError]) {
        return;
    }
}
0

There are 0 answers