0

I am trying to encode and decide the data and encoding working perfectly fine but when i use Decoder to decode the data , my decoder function is throwing me an error . Please look at my code and let me know what should i do in order to properly decode the data . The issue after debugging I found is decoder block does not proceed further next to switch , instead on type it returns and error with , DecodingKey type not found.

type = try container.decode(WorkoutType.self, forKey: .type) this is the line where it does not proceed further when i wanna decode the data.

here is my code

struct OverviewWorkout : Codable {

enum WorkoutType: String , Codable {
    case workout
    case coach
    case bodyArea
    case challenge
    case title
    case group
    case trainer
}


enum WorkoutsData  {
  case workout(Workout)
  case challenge(Workout)
  case group([Workout])
  case trainer([Trainer])
  case bodyArea([Workout])
  case coach(CoachInstruction)
  case title(Title)

}

var type: WorkoutType
var data : WorkoutsData

init(from decoder: Decoder) throws {
    print("decoder called")
    let container = try decoder.container(keyedBy: CodingKeys.self)
    type =  try container.decode(WorkoutType.self, forKey: .type)
    switch type {
    case .workout, .challenge:
        let data = try container.decode(Workout.self, forKey: .data)
        self.data = .workout(data)
    case .coach:
        let data = try container.decode(CoachInstruction.self, forKey: .data)
        self.data = .coach(data)

    case .bodyArea:
        let data = try container.decode([Workout].self, forKey: .data)
        self.data = .bodyArea(data)

    case .title:
        let data = try container.decode(Title.self, forKey: .data)
        self.data = .title(data)

    case .group:
       let data = try container.decode([Workout].self, forKey: .data)
        self.data = .group(data)

      // trainer data
        case .trainer:
          let  data = try container.decode([Trainer].self, forKey: .data)
            self.data = .trainer(data)

        }

        print("decodable called")
        
    }
    


    private enum CodingKeys: String, CodingKey {
        case type,data

    }
}

extension OverviewWorkout {
    struct Title: Codable {
        let title: String
    }
}


extension OverviewWorkout {
    
    func encode(to encoder: Encoder) throws {
        var container = encoder.container(keyedBy: CodingKeys.self)
        print(container)
        switch data {
        case .workout(let workout):
            try container.encode(workout, forKey: .data)
        case .bodyArea(let bodyarea):
            try container.encode(bodyarea, forKey: .data)
        case .title(let title):
            try container.encode(title, forKey: .data)
        case .coach(let coach):
            try container.encode(coach, forKey: .data)
        case .trainer(let trainer):
            try container.encode(trainer, forKey: .data)
        case .group(let group):
            try container.encode(group, forKey: .data)

        default:
            print("out of range")
        }
      }
}

here is the error I am having whenever init(from decoder: Decoder) throws is called keyNotFound(CodingKeys(stringValue: "type", intValue: nil), Swift.DecodingError.Context(codingPath: [_JSONKey(stringValue: "Index 0", intValue: 0)], debugDescription: "No value associated with key CodingKeys(stringValue: "type", intValue: nil) ("type").", underlyingError: nil)) keyNotFound(CodingKeys(stringValue: "type", intValue: nil), Swift.DecodingError.Context(codingPath: [_JSONKey(stringValue: "Index 0", intValue: 0)], debugDescription: (lldb)

11
  • Show the JSON that causes the error... Commented Nov 18, 2021 at 23:18
  • please see , i have added json file Commented Nov 18, 2021 at 23:28
  • the issue is somewhere here. type = try container.decode(WorkoutType.self, forKey: .type). . because it does not go to the next step where i am using switch statements because it does not find the coding key "type" Commented Nov 18, 2021 at 23:29
  • That is not a valid JSON file. That looks like it may be what Xcode prints out to the log, but it's definitely not true JSON. Commented Nov 18, 2021 at 23:30
  • 1
    unless I'm completely misreading this, the reason that the decoder can't decode type is that the encoder isn't encoding it. I can't see a try container.encode(type, forKey: .type) anywhere in encode(to:) Commented Nov 19, 2021 at 0:22

1 Answer 1

0

So the issue was I was just encoding the data not the key , That is why i was literally having the issue the key was Nil while decoding the data. I have just put one line of code to encode the key and thats all the issue had gone.

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.