I am receiving three errors in my viewController and I can not figure out how to fix them these errors are 1.) extension Declaration is only valid at file scope, 2.)Value of type 'Unable to infer type of a closure parameter 'result' in the current context ' 3.) URLSession has no member 'request'. None of these errors make any sense to me because I have already defined result as a member of URLSession. Im not sure if Xcode is glitching, or if these errors are present in my code and if so can anyone point them out and how to fix?
import UIKit
import Foundation
enum NetworkError: Error {
case badRequest
case decodingError
}
struct Category: Codable {
let CategoryId: String
let CategoryThumb: String
let CategoryDescription: String
let categories: [Category]
class ViewController: UIViewController, UITableViewDelegate, UITableViewDataSource {
struct Constants {
static let categoriesurl = URL(string: "https://www.themealdb.com/api/json/v1/1/categories.php")
static let filterListurl = URL(string: "https://www.themealdb.com/api/json/v1/1/filter.php?c=Beef")
static let mealByIdurl = URL(string: "https://www.themealdb.com/api/json/v1/1/lookup.php?i=52874")
}
//create table view to test results from API endpoint
let table: UITableView = {
let table = UITableView()
table.register(UITableViewCell.self, forCellReuseIdentifier: "cell")
return table
}()
private var categories: [Category] = []
override func viewDidLoad() {
super.viewDidLoad()
view.addSubview(table)
table.delegate = self
table.dataSource = self
fetch()
}
override func viewDidLayoutSubviews() {
super.viewDidLayoutSubviews()
table.frame = view.bounds
}
func fetch() {
URLSession.shared.request(url: Constants.categoriesurl, returning: [Category].self
) {[weak self] result in
switch result {
case.success(let category):
DispatchQueue.main.async {
self?.category = category
self?.table.reloadData()
}
case.failure(let error):
print(error )
}
}
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return categories.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = table.dequeueReusableCell(withIdentifier: "cell", for: indexPath)
cell.textLabel?.text = categories[indexPath.row].CategoryId
return cell
}
}
extension URLSession {
func request<T: Codable>(url: URL?,returning: T.Type,completion: @escaping (Result<T, Error>) -> Void) {
guard let url = url else {
//we create a enum for network error that will return an error if the API end point is a bad request,or if unable decoding the Json data
//Create a urls that fetches the data from each API end points
NetworkError.badRequest
return
}
let task = dataTask(with: url) {data, _, error in
guard let data = data else {
if let error = error {
NetworkError.badRequest
} else {
NetworkError.decodingError
}
return
} //if your data is return sucessfully from the API
do {
let Result = try! JSONDecoder().decode(returning, from: data)
completion(.success(Result))
}
catch {
NetworkError.badRequest
} //if the data does not return an error will be met
}
task.resume()
}
}
}
CodePudding user response:
You're declaring an extension within the scope of a struct declaration. Your extension has to be declared outside of any other scope.
Because you extension was rejected, The system doesn't know what kind of parameter
request
should take and since you haven't declared the type ofresult
inside the closure, it has no way to infer what what type it should have and the error message tells you just thatURLSession does not have a member named
request
because your extension was rejected (because of error #1).
The first step to fix this would be to move your extension outside of the scope of struct Category
CodePudding user response:
- extension Declaration is only valid at file scope - Extension go inside a struct or a class, here you are declaring urlSession extension inside Category struct, please declare it outside.
- Value of type 'Unable to infer type of a closure parameter 'result' in the current context ' - Please let us know the line of error, mostly this type of error would require to handle
do-try-catch
. - When the extension is placed outside the struct, this error would go.