Home > Software engineering >  JSON Array to model using Alamofire
JSON Array to model using Alamofire

Time:02-08

I'm creating a UITableView that will display this response in every cell. The problem is, I do not know how to parse this response to the model.

Here is the response from the api

[
"electronics",
"jewelery",
"men's clothing",
"women's clothing"
]

Here is the code for the the ViewController

class HomeViewController: UIViewController {
    
    @IBOutlet var tableView: UITableView!
    var category: [Category] = []
    override func viewDidLoad() {
        super.viewDidLoad()

        tableView.delegate = self
        tableView.dataSource = self

        
        guard let url = URL(string: "\(Constants.url.baseUrl)\(Constants.url.category)") else {
            return
        }
        
        
        AF.request(url).responseDecodable(of: [Category].self) { response in
            guard let categories = response.value else {
                return
            }
            DispatchQueue.main.async { [weak self] in
                
                self?.tableView.reloadData()
            }
            
            
        }

    }

}

extension HomeViewController: UITableViewDataSource, UITableViewDelegate {
    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        print("category count", category.count)

        return category.count
    }

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        guard let cell = tableView.dequeueReusableCell(withIdentifier: Constants.identifiers.categoryTableViewCell) as? CategoryTableViewCell else{
            return UITableViewCell()
        }
        cell.configureTableViewCell(with: self.category[indexPath.row])
        return cell

    }


}

Here is my model

struct Category: Codable {
}

I would greatly appreciate any help. Thank you in advanced!

CodePudding user response:

Here is the answer to your problem...

So your model class will look something like this :

import Foundation
struct Category: Codable {

    enum CodingKeys: String, CodingKey {

    }

    init(from decoder: Decoder) throws {
        let values = try decoder.container(keyedBy: CodingKeys.self)
    }

}

Now you can use this as one of the three following ways to parse the data :

1.Using Codable Mapping :

let url = URL(string: "http://www.google.com")
let task = URLSession.shared.dataTask(with: url!) { (data, response, error) in  
let jsonDecoder = JSONDecoder()
let responseModel = try jsonDecoder.decode(Category.self, from: data!)

}
task.resume()

2.Using ObjectMapper

// Convert JSON String to Model
let responseModel = Mapper<Category>().map(JSONString: JSONString)

// Create JSON String from Model
let JSONString = Mapper().toJSONString(responseModel, prettyPrint: true)

3.Using Dictionary Mapping

let url = URL(string: "http://www.google.com")
let task = URLSession.shared.dataTask(with: url!) { (data, response, error) in

    let someDictionaryFromJSON = try JSONSerialization.jsonObject(with: 
    data, options: .allowFragments) as! [String: Any]
    let category = Category(someDictionaryFromJSON)

}
task.resume()

CodePudding user response:

Here is your answer

guard let url = URL(string: "https://fakestoreapi.com/products/categories") else {
    return
}
AF.request(url).responseData(completionHandler: { response in
    guard let responseData = response.data else {
        return
    }
    let categoriesData = try? JSONDecoder().decode(Categories.self, from: responseData)
    print(categoriesData!)
})

Parsing

typealias Categories = [String]

Response

enter image description here

Here in your case, your response returns only a string array so can't need to create the Model Class for this you can achieve by typealias variable

If there are any other more objects in your response then you can do like this

struct Category: Codable {
    let id: Int?
    var name: String?

    enum CodingKeys: String, CodingKey {
        case id = "ID"
        case name = "Name"
    }
    
    init(from decoder: Decoder) throws
        {
        let values = try decoder.container(keyedBy: CodingKeys.self)
        id = try? values.decode(Int.self, forKey: .id)
        name = try? values.decode(String.self, forKey: .name)
    }
}

guard let url = URL(string: "https://fakestoreapi.com/products/categories") else {
        return
}
AF.request(url).responseData(completionHandler: { response in
    guard let responseData = response.data else {
        return
    }
    let categoryData = try? JSONDecoder().decode(Category.self, from: responseData)
    print(categoryData.id)
    print(categoryData.name)
})
  •  Tags:  
  • Related