Добавление атрибута "Не выполнять резервное копирование" в иерархию папок в iOS 5.0.1

Ссылка iCloud + Хранение медиафайлов в папке iPhone Documents, в которой показано, как установить атрибут iOS 5.0.1 "Не архивировать" для файла.

Есть ли эффективный способ сделать это для всей иерархии папок/файлов? Например, мое приложение создает /Library/PrivateDocs и заполняет его несколькими папками, подпапками и файлами. Могу ли я просто установить атрибут do-not-backup в папке верхнего уровня или он должен быть установлен в каждом отдельном файле и папке под этим тоже?

И, если он должен быть установлен в каждой папке/подпапке, какой эффективный способ сделать это?

Ответ 1

Вы можете поместить один конкретный каталог в каталог dir для этой цели, поместить все внутри и только пометить этот единственный каталог как do-not-backup с помощью

 addSkipBackupAttributeToItemAtURL

показанный в статье, которую вы связали, или используйте этот, который использует путь вместо URL-адреса:

+ (void)addSkipBackupAttributeToPath:(NSString*)path {
    u_int8_t b = 1;
    setxattr([path fileSystemRepresentation], "com.apple.MobileBackup", &b, 1, 0, 0);
}

пример с использованием каталога:

NSString *docsDirPath = [(AppDelegate*)[[UIApplication sharedApplication] delegate] applicationDocumentsDirectory];
NSString *yourContentsDirPath = [docsDirPath stringByAppendingPathComponent:gContentsDirName];

[Utilities addSkipBackupAttributeToPath:yourContentsDirPath];

[EDIT]

Я забыл использовать этот метод в делегате для получения документа dir:

- (NSString *)applicationDocumentsDirectory {

    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *basePath = ([paths count] > 0) ? [paths objectAtIndex:0] : nil;
    return basePath;
}

Ответ 2

Для всех моих друзей, которые нуждаются в Swift - просто посмотрите ниже (iOS8.0)

func addSkipBackupAttributeToItemAtURL(URL:NSURL) ->Bool{

let fileManager = NSFileManager.defaultManager()
assert(fileManager.fileExistsAtPath(URL.absoluteString))

var error:NSError?
let success:Bool = URL.setResourceValue(NSNumber.numberWithBool(true),forKey: NSURLIsExcludedFromBackupKey, error: &error)

if !success{

    println("Error excluding \(URL.lastPathComponent) from backup \(error)")
}

return success;

}

Ответ 3

Для меня, в Swift, ранее ответные функции не совсем сработали. В частности, строка подтверждения не удалась. Мне нужно было обновить его из URL.absoluteString! на URL.path! Итак, в конце мой выглядит следующим образом:

func addSkipBackupAttributeToItemAtURL(URL:NSURL) ->Bool{

    let fileManager = NSFileManager.defaultManager()
    assert(fileManager.fileExistsAtPath(URL.path!))

    var error:NSError?
    let success:Bool = URL.setResourceValue(NSNumber(bool: true),forKey: NSURLIsExcludedFromBackupKey, error: &error)

    if !success{
        println("Error excluding \(URL.lastPathComponent) from backup \(error)")
    }

    return success;
}

Ответ 4

Возможно, это помогло бы кому-то использовать быстрый 2:

Как раз перед @UIApplicationMain добавьте это:

extension NSFileManager{
    func addSkipBackupAttributeToItemAtURL(url:NSURL) throws {
        try url.setResourceValue(true, forKey: NSURLIsExcludedFromBackupKey)
    }
}

В своем lazy var persistentStoreCoordinator: NSPersistentStoreCoordinator? = { после объявления вашего URL-адреса вы можете добавить это:

 do {
            let url = url
            try NSFileManager.defaultManager().addSkipBackupAttributeToItemAtURL(url)

        } catch {
            // Handle error here
            print("Error: \(error)")
        }

Ответ 5

Исправление по вышеуказанному методу, используйте это для быстрого

 func addSkipBackupAttributeToItemAtURL(URL:NSURL) ->Bool {

    let fileManager = NSFileManager.defaultManager()
    assert(fileManager.fileExistsAtPath(URL.absoluteString!))

    var error:NSError?
    let success:Bool = URL.setResourceValue(NSNumber(bool: true),forKey: NSURLIsExcludedFromBackupKey, error: &error)

    if !success{

        println("Error excluding \(URL.lastPathComponent) from backup \(error)")
    }

    return success;
}

Ответ 6

вы можете сделать следующее в swift:

func addSkipBackupAttributeToItemAtPath(path:String) -> Bool {


    let filePath = path.fileSystemRepresentation()
    let attrName  = "com.apple.MobileBackup"

    var attrValue : uint_fast8_t = 1

    let result = setxattr(filePath, attrName, &attrValue, sizeof(attrValue.dynamicType), 0, 0)

    return result == 0
}