A Tyshka
A Tyshka

Reputation: 4100

Why is this plist read/write failing?

I'm following along an iOS tutorial and I've run into trouble with plists. I have this code for a reflection, a model object in my app:

struct Reflection {
let title: String
let body: String
let author: String
let favorite: Bool
let creationDate: Date
let id: UUID
}

extension Reflection {
var plistRepresentation: [String: AnyObject] {
    return [
        "title": title as AnyObject,
        "body": body as AnyObject,
        "author": author as AnyObject,
        "favorite": favorite as AnyObject,
        "creationDate": creationDate as AnyObject,
        "id": id as AnyObject
    ]
}

init(plist: [String: AnyObject]) {
    title = plist["title"] as! String
    body = plist["body"] as! String
    author = plist["author"] as! String
    favorite = plist["favorite"] as! Bool
    creationDate = plist["creationDate"] as! Date
    id = plist["id"] as! UUID
}
}

Then I have this storage controller:

class StorageController {
fileprivate let documentsDirectoryURL = FileManager.default
    .urls(for: .documentDirectory, in: .userDomainMask)
    .first!

fileprivate var notesFileURL: URL {
    return documentsDirectoryURL
        .appendingPathComponent("Notes")
        .appendingPathExtension("plist")
}

func save(_ notes: [Reflection]) {
    let notesPlist = notes.map { $0.plistRepresentation } as NSArray
    notesPlist.write(to: notesFileURL, atomically: true)
}

func fetchNotes() -> [Reflection] {

    guard let notePlists = NSArray(contentsOf: notesFileURL) as? [[String: AnyObject]] else {
        print("No notes")
        return []
    }
    print("Notes found")
    return notePlists.map(Reflection.init(plist:))
}
}

I get no errors when I call save() and it attempts to write to the plist. However, when I call fetchNotes() it prints "No Notes", implying that the array using those contents is nil or that it cannot be cast to a dictionary. Why would this be?

Upvotes: 2

Views: 108

Answers (1)

rob mayoff
rob mayoff

Reputation: 386038

A UUID is not a valid element of a property list. You need to store it as a string in the property list, e.g.

“id”: id.uuidString as AnyObject

and convert it back like this:

id = UUID(uuidString: plist[“id”] as! String)!

Upvotes: 3

Related Questions