NSKeyedUnarchiver returning nil when retrieving custom class

ewcrow

In my view controller, I have a custom class store in an array. I was using NSKeyedArchiver to store data but I was using the depreciated version NSKeyedUnarchiver.unarchiveObject(withFile: object.ArchiveURL.path) as? [object].

Now I have decided to update it to: let data = try Data(contentsOf: filePath) let object = try NSKeyedUnarchiver.unarchiveTopLevelObjectWithData(data)

Here is my save function:

 let data = try NSKeyedArchiver.archivedData(withRootObject: object, requiringSecureCoding: false)
 try data.write(to: filePath)

When I return object from the Unarchiver it returns nil. I'm not sure why. This is my custom class:

class object: NSObject, NSCoding {
   var name: String
   var photo: UIImage

    struct PropertyKey {
        static let name = "name"
        static let photo = "photo"
    }

    func encode(with aCoder: NSCoder) {
        aCoder.encode(self.name, forKey: PropertyKey.name)
        aCoder.encode(self.photo, forKey: PropertyKey.photo)
    }

    required convenience init?(coder aDecoder: NSCoder) {
         // The name is required. If we cannot decode a name string, the initializer should     fail.
         guard let name = aDecoder.decodeObject(forKey: PropertyKey.name) as? String else {
             os_log("unable to find name", log: OSLog.default, type: .debug)
             return nil
         }

         guard let photo = aDecoder.decodeObject(forKey: PropertyKey.photo) as? UIImage else  {
              os_log("unable to find photo", log: OSLog.default, type: .debug)
              return nil
         }


        // Must call designated initializer.
        self.init(name: name, photo: photo)
   }

   init?(name: String, photo: UIImage) {
        // Initialize stored properties.
        self.name = name
        self.photo = photo

   }
}
Awais

You can use this method to unarchive the data. https://developer.apple.com/documentation/foundation/nskeyedunarchiver/2963379-unarchivedobject

NSKeyedUnarchiver.unarchivedObject(ofClasses:from:)

You can write your unarchiving code as;

let data = try Data(contentsOf: filePath)
let object = try NSKeyedUnarchiver.unarchivedObject(ofClasses:[object.self, UIImage.self], from: data)

Hopefully, it works.

PS. One tip about naming classes. They should always start with capital letter.

EDIT: You should add UIImage.self also when trying to unarchive. and you should change your archive method as seen below.

NSKeyedArchiver.archivedData(withRootObject: data, requiringSecureCoding: true)

Your model should also satisfy NSSecureCoding protocol when using this unarchive method.

extension object : NSSecureCoding {
    static var supportsSecureCoding: Bool {
       return true
    }
}

Collected from the Internet

Please contact [email protected] to delete if infringement.

edited at
0

Comments

0 comments
Login to comment

Related

NSKeyedUnarchiver unarchiveObjectWithData returning nil

NSKeyedUnarchiver.unarchivedObject returning nil for dictionary

custom class method returning nil Swift IOS

table view cell of custom class returning nil

Delegate is nil when custom class is created for NSTableview?

UITableViewCell super class property returning nil when set from UITableView

Custom NSFormatter returning nil in swift

UIFont returning nil for custom font

ParseMultipartForm() returning nil when ErrNotMultipart

NSKeyedUnarchiver.unarchiveTopLevelObjectWithData return nil

Casting custom annotation view always returning nil

UIImageView in custom UICollectionViewCell returning nil all the time

ChildNode of custom type is returning Nil on Swift Playground

custom tableview cell xib outlets returning nil

ruby Class.new returning nil in rspec

Delegate Returning nil, not in ViewController but on Delegate creating class

table returning nil value when calling function

When querying Parse pointer -- it is returning nil

string.find not returning nil when searching for "."

Why is this method not returning nil when a and b are equal?

Retrieving tread depth when stairs not of Stairs class

$find returning null when retrieving telerik controls in javascript

Retrieving keychain value with A0SimpleKeychain returning nil in OS10

Swift - Why does a passed custom class retain changed properties when returning to previous view?

Custom Segue in Swift 2.0 : destinationViewController's navigationController property returning nil

Custom Controller Action update_attribute returning nil

incompatible types when returning a Class

Why is this Singleton Location Manager class returning a nil Location?

CollectionView IBOutlet inside a UIView class is returning nil - only sometimes?