Swift 4 http get and iterate the JSON response

Asked

Viewed 395 times

0

Hello, I am learning Swift and am making a GET request via URL that returns me a JSON with this structure.

{
 "data": {
 "response": [
 "https://s3.amazonaws.com/meusite/minhapasta/banners/banner-01.png",
 "https://s3.amazonaws.com/meusite/minhapasta/banners/banner-02.png",
 "https://s3.amazonaws.com/meusite/minhapasta/banners/banner-03.png"
 ]
 }
 }

.

In the Playground I am doing so to request the JSON

import Foundation
import PlaygroundSupport

PlaygroundPage.current.needsIndefiniteExecution = true

// Seta a URL
let url = URL(string: "https://adm.meusite.com.br/api/app/v1/1/usuarios/banners")!
    // faz a requisição retornando data, response, error
    let task = URLSession.shared.dataTask(with: url) { (data, response, error) in
    //checa se tem erro
    guard error == nil else {
        // Exibe o erro
        print(error?.localizedDescription ?? "")
        // encerra e não executa o restante do código
        return
    }
    // Remove do optional
    if  let data = data,
        // pega o conteudo do JSON converte para string
        let contents = String(data: data, encoding: String.Encoding.utf8) {
        // Printa o JSON como String
        print(contents)

    }

 }
// Encerra a requisição
task.resume()

I would like to know how to iterate this JSON, replacing this excerpt with the iteration of dicionary:

// pega o conteudo do JSON converte para string
let contents = String(data: data, encoding: String.Encoding.utf8) {
        // Printa o JSON como String
        print(contents)

    }

1 answer

0


You can use a method of JSONSerialization called jsonObject(with: Data) that Convert the data returned by the API in an Object of type Any. Then you need to cast the type Any for dictionary [String:Any] and access the elements by also making the subsequent Any for the corresponding type:

do {
    if let jsonObject = (try JSONSerialization.jsonObject(with: data)) as? [String: Any],
        let dictionary = jsonObject["data"] as? [String: Any],
        let response = (dictionary["response"] as? [String])?.flatMap({URL(string: $0)}) {
        print(response)  // "[https://s3.amazonaws.com/meusite/minhapasta/banners/banner-01.png, https://s3.amazonaws.com/meusite/minhapasta/banners/banner-02.png, https://s3.amazonaws.com/meusite/minhapasta/banners/banner-03.png]\n"
        for url in response {
            print(url)
        }
    }
} catch {
    print(error)
}

Another option you have if you are using Xcode 9.x • Swift 4 is to create a structure Codable:

struct Root: Codable {
    let data: Response
    struct Response: Codable {
        let response: [URL]
    }
}

And then just use the JSONDecoder to decode the data returned by your API:

do {
    let response = try JSONDecoder().decode(Root.self, from: data).data.response
    print(response)  // "[https://s3.amazonaws.com/meusite/minhapasta/banners/banner-01.png, https://s3.amazonaws.com/meusite/minhapasta/banners/banner-02.png, https://s3.amazonaws.com/meusite/minhapasta/banners/banner-03.png]\n"
    for url in response {
        print(url)
    }
} catch {
    print(error)
}
  • I’m using Xcode 9 with Swift 4 even... And if json looks like this: {"date": [{"id": "1","Attributes": {"fantasy-name": "Company 1","telephones": [{"numero": "(00) 0000-0000"}]}},{"id": "2","Attributes": {"fantasy-name": "Company 2","telephones": [{"numero": "(00) 0000-0000"}]}}]}. What would class (or struct) look like? The date being an Array of Dictionaries. And where do I read about it? has some hint?

  • @Carlosfagianijr This structure would be a little more complicated, but once you have understood how to structure your data becomes much easier, it’s just a matter of practice. Regarding some reference I will look for the documentation and pass you the links. I think it would be better to open another question that I put the answer there for you.

  • 1

    https://developer.apple.com/documentation/foundation/archives_and_serialization/encoding_and_decoding_custom_types e https://developer.apple.com/documentation/foundation/archives_and_serialization/using_json_with_custom_types

  • I have a similar case but my json comes in a different way [ { "id": "1", "Description": "teste3", "live": "https://...." , "Thumb": "http...", "online": true }, { "id": "1", "Description": "teste2", "live": "https://..." , "Thumb": "http...", "online": true }] could not implement with the example of vcs can help me

  • @Joãovitor whatever the format of the data the most that can happen is you have to create a custom Decoder initializer.

  • can you send me an example

  • This also depends on what kind of data. Date?

  • picked up the answer of the alembic usually caught the Sponse.data

  • just determine in Jsondecoder which dateDecodingStrategy. If your date has fractional Seconds there gets more complicated

  • https://stackoverflow.com/questions/46458487/how-to-convert-a-date-string-with-optional-fractional-seconds-using-codable-in-s/46458771?s=4|0.0000#46458771

Show 6 more comments

Browser other questions tagged

You are not signed in. Login or sign up in order to post.