Моя цель - выбрать ближайшие к моему месту рестораны и отобразить их для пользователя в виде таблицы. Мне нужно декодировать этот ответ API и получить доступ к некоторым его парам значений (точнее, «name», «url» и «aggregate_rating»). Но когда я пытаюсь сериализовать JSON ответ и распечатать его на терминале, это то, что я получаю (я знаю, это довольно долго)
{
restaurant = {
R = {
"has_menu_status" = {
delivery = "-1";
takeaway = "-1";
};
"res_id" = 16694062;
};
apikey = e06745d59aa6170842e9760500129d63;
"average_cost_for_two" = 50;
"book_again_url" = "";
"book_form_web_view_url" = "";
cuisines = Turkish;
currency = TL;
deeplink = "zomato://restaurant/16694062";
"events_url" = "https://www.zomato.com/izmir/sen-mutfak-altievler/events#tabtop?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"featured_image" = "";
"has_online_delivery" = 0;
"has_table_booking" = 0;
id = 16694062;
"include_bogo_offers" = 1;
"is_book_form_web_view" = 0;
"is_delivering_now" = 0;
"is_table_reservation_supported" = 0;
"is_zomato_book_res" = 0;
location = {
address = "MOTOPORNE \U00c7IKMAZI SEHITLIK, NARLIDERE \nIZMIR, Altievler, Izmir";
city = Izmir;
"city_id" = 376;
"country_id" = 208;
latitude = "38.3997300000";
locality = Altievler;
"locality_verbose" = "Altievler, Izmir";
longitude = "27.0005000000";
zipcode = "";
};
"menu_url" = "https://www.zomato.com/izmir/sen-mutfak-altievler/menu?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1&openSwipeBox=menu&showMinimal=1#tabtop";
"mezzo_provider" = OTHER;
name = "Sen Mutfak";
offers = (
);
"opentable_support" = 0;
"photos_url" = "https://www.zomato.com/izmir/sen-mutfak-altievler/photos?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1#tabtop";
"price_range" = 2;
"switch_to_order_menu" = 0;
thumb = "";
url = "https://www.zomato.com/izmir/sen-mutfak-altievler?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"user_rating" = {
"aggregate_rating" = "3.4";
"rating_color" = CDD614;
"rating_obj" = {
"bg_color" = {
tint = 500;
type = lime;
};
title = {
text = "3.4";
};
};
"rating_text" = Average;
votes = 7;
};
};
},
{
restaurant = {
R = {
"has_menu_status" = {
delivery = "-1";
takeaway = "-1";
};
"res_id" = 16689453;
};
apikey = e06745d59aa6170842e9760500129d63;
"average_cost_for_two" = 100;
"book_again_url" = "";
"book_form_web_view_url" = "";
cuisines = "Fresh Fish, Seafood";
currency = TL;
deeplink = "zomato://restaurant/16689453";
"events_url" = "https://www.zomato.com/izmir/bizim-gazino-narlidere/events#tabtop?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"featured_image" = "";
"has_online_delivery" = 0;
"has_table_booking" = 0;
id = 16689453;
"include_bogo_offers" = 1;
"is_book_form_web_view" = 0;
"is_delivering_now" = 0;
"is_table_reservation_supported" = 0;
"is_zomato_book_res" = 0;
location = {
address = "Kumsal Sok. 110, Narlidere/Izmir";
city = Izmir;
"city_id" = 376;
"country_id" = 208;
latitude = "38.3995000000";
locality = Narlidere;
"locality_verbose" = "Narlidere, Izmir";
longitude = "26.9865000000";
zipcode = "";
};
"menu_url" = "https://www.zomato.com/izmir/bizim-gazino-narlidere/menu?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1&openSwipeBox=menu&showMinimal=1#tabtop";
"mezzo_provider" = OTHER;
name = "Bizim Gazino";
offers = (
);
"opentable_support" = 0;
"photos_url" = "https://www.zomato.com/izmir/bizim-gazino-narlidere/photos?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1#tabtop";
"price_range" = 3;
"switch_to_order_menu" = 0;
thumb = "";
url = "https://www.zomato.com/izmir/bizim-gazino-narlidere?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"user_rating" = {
"aggregate_rating" = "3.5";
"rating_color" = 9ACD32;
"rating_obj" = {
"bg_color" = {
tint = 500;
type = lime;
};
title = {
text = "3.5";
};
};
"rating_text" = Good;
votes = 12;
};
};
},
{
restaurant = {
R = {
"has_menu_status" = {
delivery = "-1";
takeaway = "-1";
};
"res_id" = 16694494;
};
apikey = e06745d59aa6170842e9760500129d63;
"average_cost_for_two" = 50;
"book_again_url" = "";
"book_form_web_view_url" = "";
cuisines = Turkish;
currency = TL;
deeplink = "zomato://restaurant/16694494";
"events_url" = "https://www.zomato.com/izmir/\U00e7amalti-keyfi-altievler/events#tabtop?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"featured_image" = "";
"has_online_delivery" = 0;
"has_table_booking" = 0;
id = 16694494;
"include_bogo_offers" = 1;
"is_book_form_web_view" = 0;
"is_delivering_now" = 0;
"is_table_reservation_supported" = 0;
"is_zomato_book_res" = 0;
location = {
address = "Narlidere Tansas Yolu \U00dczeri IZMIR, Altievler, Izmir";
city = Izmir;
"city_id" = 376;
"country_id" = 208;
latitude = "38.3985300000";
locality = Altievler;
"locality_verbose" = "Altievler, Izmir";
longitude = "27.0020200000";
zipcode = "";
};
"menu_url" = "https://www.zomato.com/izmir/\U00e7amalti-keyfi-altievler/menu?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1&openSwipeBox=menu&showMinimal=1#tabtop";
"mezzo_provider" = OTHER;
name = "\U00c7amalti Keyfi";
offers = (
);
"opentable_support" = 0;
"photos_url" = "https://www.zomato.com/izmir/\U00e7amalti-keyfi-altievler/photos?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1#tabtop";
"price_range" = 2;
"switch_to_order_menu" = 0;
thumb = "";
url = "https://www.zomato.com/izmir/\U00e7amalti-keyfi-altievler?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"user_rating" = {
"aggregate_rating" = 0;
"rating_color" = CBCBCB;
"rating_obj" = {
"bg_color" = {
tint = 400;
type = grey;
};
title = {
text = "-";
};
};
"rating_text" = "Not rated";
votes = 1;
};
};
},
{
restaurant = {
R = {
"has_menu_status" = {
delivery = "-1";
takeaway = "-1";
};
"res_id" = 16696143;
};
apikey = e06745d59aa6170842e9760500129d63;
"average_cost_for_two" = 25;
"book_again_url" = "";
"book_form_web_view_url" = "";
cuisines = Patisserie;
currency = TL;
deeplink = "zomato://restaurant/16696143";
"events_url" = "https://www.zomato.com/izmir/nil-pastanesi-narlidere/events#tabtop?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"featured_image" = "";
"has_online_delivery" = 0;
"has_table_booking" = 0;
id = 16696143;
"include_bogo_offers" = 1;
"is_book_form_web_view" = 0;
"is_delivering_now" = 0;
"is_table_reservation_supported" = 0;
"is_zomato_book_res" = 0;
location = {
address = "Mithatpasa Cad. No: 325/A, Narlidere / Izmir, Narlidere, Izmir";
city = Izmir;
"city_id" = 376;
"country_id" = 208;
latitude = "38.3944000000";
locality = Narlidere;
"locality_verbose" = "Narlidere, Izmir";
longitude = "27.0050000000";
zipcode = "";
};
"menu_url" = "https://www.zomato.com/izmir/nil-pastanesi-narlidere/menu?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1&openSwipeBox=menu&showMinimal=1#tabtop";
"mezzo_provider" = OTHER;
name = "Nil Pastanesi";
offers = (
);
"opentable_support" = 0;
"photos_url" = "https://www.zomato.com/izmir/nil-pastanesi-narlidere/photos?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1#tabtop";
"price_range" = 1;
"switch_to_order_menu" = 0;
thumb = "";
url = "https://www.zomato.com/izmir/nil-pastanesi-narlidere?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"user_rating" = {
"aggregate_rating" = 0;
"rating_color" = CBCBCB;
"rating_obj" = {
"bg_color" = {
tint = 400;
type = grey;
};
title = {
text = "-";
};
};
"rating_text" = "Not rated";
votes = 3;
};
};
},
{
restaurant = {
R = {
"has_menu_status" = {
delivery = "-1";
takeaway = "-1";
};
"res_id" = 16696674;
};
apikey = e06745d59aa6170842e9760500129d63;
"average_cost_for_two" = 40;
"book_again_url" = "";
"book_form_web_view_url" = "";
cuisines = Izgara;
currency = TL;
deeplink = "zomato://restaurant/16696674";
"events_url" = "https://www.zomato.com/izmir/kanat\U00e7i-h\U00fcso-narlidere/events#tabtop?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"featured_image" = "";
"has_online_delivery" = 0;
"has_table_booking" = 0;
id = 16696674;
"include_bogo_offers" = 1;
"is_book_form_web_view" = 0;
"is_delivering_now" = 0;
"is_table_reservation_supported" = 0;
"is_zomato_book_res" = 0;
location = {
address = "\U00c7ESME OTOBAN ALTI NO:2 TANSAS SERVIS YOLU \U00dcZERI\nBal\U00e7ova\nIZMIR, Narlidere, Izmir";
city = Izmir;
"city_id" = 376;
"country_id" = 208;
latitude = "38.3932000000";
locality = Narlidere;
"locality_verbose" = "Narlidere, Izmir";
longitude = "26.9890000000";
zipcode = "";
};
"menu_url" = "https://www.zomato.com/izmir/kanat\U00e7i-h\U00fcso-narlidere/menu?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1&openSwipeBox=menu&showMinimal=1#tabtop";
"mezzo_provider" = OTHER;
name = "Kanat\U00e7i H\U00fcso";
offers = (
);
"opentable_support" = 0;
"photos_url" = "https://www.zomato.com/izmir/kanat\U00e7i-h\U00fcso-narlidere/photos?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1#tabtop";
"price_range" = 2;
"switch_to_order_menu" = 0;
thumb = "";
url = "https://www.zomato.com/izmir/kanat\U00e7i-h\U00fcso-narlidere?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"user_rating" = {
"aggregate_rating" = 0;
"rating_color" = CBCBCB;
"rating_obj" = {
"bg_color" = {
tint = 400;
type = grey;
};
title = {
text = "-";
};
};
"rating_text" = "Not rated";
votes = 3;
};
};
},
{
restaurant = {
R = {
"has_menu_status" = {
delivery = "-1";
takeaway = "-1";
};
"res_id" = 16696286;
};
apikey = e06745d59aa6170842e9760500129d63;
"average_cost_for_two" = 40;
"book_again_url" = "";
"book_form_web_view_url" = "";
cuisines = Cafe;
currency = TL;
deeplink = "zomato://restaurant/16696286";
"events_url" = "https://www.zomato.com/izmir/tar\U00e7in-altievler/events#tabtop?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"featured_image" = "";
"has_online_delivery" = 0;
"has_table_booking" = 0;
id = 16696286;
"include_bogo_offers" = 1;
"is_book_form_web_view" = 0;
"is_delivering_now" = 0;
"is_table_reservation_supported" = 0;
"is_zomato_book_res" = 0;
location = {
address = "Yildirim Kemal Cad., Altievler Mah., No:16 Sahilevleri / Izmir, Altievler, Izmir";
city = Izmir;
"city_id" = 376;
"country_id" = 208;
latitude = "38.3976000000";
locality = Altievler;
"locality_verbose" = "Altievler, Izmir";
longitude = "26.9975000000";
zipcode = "";
};
"menu_url" = "https://www.zomato.com/izmir/tar\U00e7in-altievler/menu?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1&openSwipeBox=menu&showMinimal=1#tabtop";
"mezzo_provider" = OTHER;
name = "Tar\U00e7in";
offers = (
);
"opentable_support" = 0;
"photos_url" = "https://www.zomato.com/izmir/tar\U00e7in-altievler/photos?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1#tabtop";
"price_range" = 2;
"switch_to_order_menu" = 0;
thumb = "";
url = "https://www.zomato.com/izmir/tar\U00e7in-altievler?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"user_rating" = {
"aggregate_rating" = 0;
"rating_color" = CBCBCB;
"rating_obj" = {
"bg_color" = {
tint = 400;
type = grey;
};
title = {
text = "-";
};
};
"rating_text" = "Not rated";
votes = 1;
};
};
},
{
restaurant = {
R = {
"has_menu_status" = {
delivery = "-1";
takeaway = "-1";
};
"res_id" = 16691486;
};
apikey = e06745d59aa6170842e9760500129d63;
"average_cost_for_two" = 70;
"book_again_url" = "";
"book_form_web_view_url" = "";
cuisines = "Restaurant Cafe";
currency = TL;
deeplink = "zomato://restaurant/16691486";
"events_url" = "https://www.zomato.com/izmir/mavi-yesil-restaurant-narlidere/events#tabtop?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"featured_image" = "";
"has_online_delivery" = 0;
"has_table_booking" = 0;
id = 16691486;
"include_bogo_offers" = 1;
"is_book_form_web_view" = 0;
"is_delivering_now" = 0;
"is_table_reservation_supported" = 0;
"is_zomato_book_res" = 0;
location = {
address = "Mithatpasa Cad. No:465 \U00c7esme Otoban Girisi Karsisi, Narlidere, Izmir";
city = Izmir;
"city_id" = 376;
"country_id" = 208;
latitude = "38.3956092539";
locality = Narlidere;
"locality_verbose" = "Narlidere, Izmir";
longitude = "26.9942235947";
zipcode = "";
};
"menu_url" = "https://www.zomato.com/izmir/mavi-yesil-restaurant-narlidere/menu?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1&openSwipeBox=menu&showMinimal=1#tabtop";
"mezzo_provider" = OTHER;
name = "Mavi Yesil Restaurant";
offers = (
);
"opentable_support" = 0;
"photos_url" = "https://www.zomato.com/izmir/mavi-yesil-restaurant-narlidere/photos?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1#tabtop";
"price_range" = 3;
"switch_to_order_menu" = 0;
thumb = "";
url = "https://www.zomato.com/izmir/mavi-yesil-restaurant-narlidere?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"user_rating" = {
"aggregate_rating" = 0;
"rating_color" = CBCBCB;
"rating_obj" = {
"bg_color" = {
tint = 400;
type = grey;
};
title = {
text = "-";
};
};
"rating_text" = "Not rated";
votes = 3;
};
};
},
{
restaurant = {
R = {
"has_menu_status" = {
delivery = "-1";
takeaway = "-1";
};
"res_id" = 16696730;
};
apikey = e06745d59aa6170842e9760500129d63;
"average_cost_for_two" = 50;
"book_again_url" = "";
"book_form_web_view_url" = "";
cuisines = Izgara;
currency = TL;
deeplink = "zomato://restaurant/16696730";
"events_url" = "https://www.zomato.com/izmir/mangal-borsasi-altievler/events#tabtop?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"featured_image" = "";
"has_online_delivery" = 0;
"has_table_booking" = 0;
id = 16696730;
"include_bogo_offers" = 1;
"is_book_form_web_view" = 0;
"is_delivering_now" = 0;
"is_table_reservation_supported" = 0;
"is_zomato_book_res" = 0;
location = {
address = "Narlidere Sehitlik Karsisi, Altievler, Izmir";
city = Izmir;
"city_id" = 376;
"country_id" = 208;
latitude = "38.3960000000";
locality = Altievler;
"locality_verbose" = "Altievler, Izmir";
longitude = "26.9978000000";
zipcode = "";
};
"menu_url" = "https://www.zomato.com/izmir/mangal-borsasi-altievler/menu?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1&openSwipeBox=menu&showMinimal=1#tabtop";
"mezzo_provider" = OTHER;
name = "Mangal Borsasi";
offers = (
);
"opentable_support" = 0;
"photos_url" = "https://www.zomato.com/izmir/mangal-borsasi-altievler/photos?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1#tabtop";
"price_range" = 2;
"switch_to_order_menu" = 0;
thumb = "";
url = "https://www.zomato.com/izmir/mangal-borsasi-altievler?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"user_rating" = {
"aggregate_rating" = 0;
"rating_color" = CBCBCB;
"rating_obj" = {
"bg_color" = {
tint = 400;
type = grey;
};
title = {
text = "-";
};
};
"rating_text" = "Not rated";
votes = 2;
};
};
},
{
restaurant = {
R = {
"has_menu_status" = {
delivery = "-1";
takeaway = "-1";
};
"res_id" = 16695847;
};
apikey = e06745d59aa6170842e9760500129d63;
"average_cost_for_two" = 40;
"book_again_url" = "";
"book_form_web_view_url" = "";
cuisines = "Turkish Pizza";
currency = TL;
deeplink = "zomato://restaurant/16695847";
"events_url" = "https://www.zomato.com/izmir/annem-pide-narlidere/events#tabtop?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"featured_image" = "";
"has_online_delivery" = 0;
"has_table_booking" = 0;
id = 16695847;
"include_bogo_offers" = 1;
"is_book_form_web_view" = 0;
"is_delivering_now" = 0;
"is_table_reservation_supported" = 0;
"is_zomato_book_res" = 0;
location = {
address = "MITHAT PASA CAD. NO:349, Narlidere, Izmir";
city = Izmir;
"city_id" = 376;
"country_id" = 208;
latitude = "38.3945000000";
locality = Narlidere;
"locality_verbose" = "Narlidere, Izmir";
longitude = "27.0044000000";
zipcode = "";
};
"menu_url" = "https://www.zomato.com/izmir/annem-pide-narlidere/menu?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1&openSwipeBox=menu&showMinimal=1#tabtop";
"mezzo_provider" = OTHER;
name = "Annem Pide";
offers = (
);
"opentable_support" = 0;
"photos_url" = "https://www.zomato.com/izmir/annem-pide-narlidere/photos?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1#tabtop";
"price_range" = 2;
"switch_to_order_menu" = 0;
thumb = "";
url = "https://www.zomato.com/izmir/annem-pide-narlidere?utm_source=api_basic_user&utm_medium=api&utm_campaign=v2.1";
"user_rating" = {
"aggregate_rating" = 0;
"rating_color" = CBCBCB;
"rating_obj" = {
"bg_color" = {
tint = 400;
type = grey;
};
title = {
text = "-";
};
};
"rating_text" = "Not rated";
votes = 2;
};
};
}
)
Это моя пользовательская структура
import Foundation
struct User_rating: Codable {
var aggregate_rating: String
}
struct Restaurant: Codable {
var name: String
var url: String
var thumb: String
var user_rating: User_rating
var photos_url: String
}
Здесь я сериализирую JSON ответ:
import UIKit
import Foundation
import CoreLocation
class RestaurantTableViewController: UITableViewController, CLLocationManagerDelegate {
let apiKey: String = "e06745d59aa6170842e9760500129d63"
let cellIdentifier: String = "restaurantCell"
var restaurants = [Restaurant]()
var restaurantImages: [URL] = []
var locationManager = CLLocationManager()
// MARK: Lifecycle methods
override func viewDidLoad() {
super.viewDidLoad()
let urlString = """
https://developers.zomato.com/api/v2.1/geocode?lat=\(locationManager.location.coordinate.latitude)&lon=\(locationManager.location.coordinate.longitude)
"""
let url = URL(string: urlString)
if url != nil {
var request = URLRequest(url: url!)
request.httpMethod = "GET"
request.addValue("application/json", forHTTPHeaderField: "Accept")
request.addValue(apiKey, forHTTPHeaderField: "user-key")
URLSession.shared.dataTask(with: request) { (data, response, error) in
guard let data = data, error == nil else { return }
let httpResponse = response as! HTTPURLResponse
if httpResponse.statusCode == 200 {
do {
let json = try JSONSerialization.jsonObject(with: data, options: .allowFragments) as! [String:Any]
print(json) // Prints the response given above
} catch _ {
}
}
}.resume()
}
}
}
Я следовал нескольким SO-ответам и другим руководствам. Любая помощь приветствуется.