ItsMoShehab
ItsMoShehab

Reputation: 53

Edit a struct in UserDefaults without losing data Swift

I have an app that have a struct (lets call it Notes). I also have an array of Notes. I stored this array in UserDefaults using codable and decode and encode. Retrieve Code:

if let data = UserDefaults.standard.value(forKey:"NotesArray") as? Data {
        let decodedSports = try? PropertyListDecoder().decode([Notes].self, from: data)
        NotesArray = decodedSports ?? []
}

and the set code:

UserDefaults.standard.set(try? PropertyListEncoder().encode(NotesArray), forKey:"NotesArray")

My app is already up and running. Now let us say I have 'createdDate' and 'modifiedDate' variables in this struct. And now after a while I want to add a new variable called 'editable'.

How can I do that without losing the existing data in the array? I have searched a lot and couldn't find any method to solve this issue.

Upvotes: 2

Views: 186

Answers (2)

Gereon
Gereon

Reputation: 17864

You have basically two options:

Either add the new properties as Optionals, and deal with possible nil values everywhere you use them.

Or, localize dealing with nils once in the decoder.

Let's say you have

struct Notes: Codable {
   let text: String
}

now. Adding e.g. createdDate could be done like this:

struct Notes: Codable {
  let text: String
  let createdDate: Date

  init(from decoder: Decoder) throws {
    let container = try decoder.container(keyedBy: CodingKeys.self)
    self.text = try container.decode(String.self, forKey: .text)
    let createdDate = try container.decodeIfPresent(Date.self, forKey: .createdDate)
    self.createdDate = createdDate ?? Date(timeIntervalSince1970: 0) // or whatever default date you want to use
}

Upvotes: 5

Joby Ingram-Dodd
Joby Ingram-Dodd

Reputation: 730

I think you can just add the field to the struct as an optional

struct Notes: Codable{
    var date: Date
    var modifiedDate: Date
    var editable: Bool?
}

Then you can set the field to editable as you need to, but it shouldn't mater if the other items in the array don't have the field as it is optional.

NotesArray[0].editable = true

Upvotes: 1

Related Questions