ios – Why is not my inner API construction executing efficiently in SwiftUI?


I’m a noob and I’m puzzled about my downside. My understanding may be restricted, I appeared up some similiar questions and I discover completely different issues, like my lacking init (I’ve no clue how init works).

So! I attempt to use an exterior API through JSON. You may discover it right here (https://www.abgeordnetenwatch.de/api/v2/politicians). My Code was working fantastic, until i needed so as to add an inner construction “occasion” (in my code “partei”), subsequent to my working “Politician” construction. After analysis, I believed I have to construct the code construction like in my code. I used completely different names for id and label, to make it work through codingkeys.

I expertise these bugs at the moment

“58:28 Generic parameter ‘T’ couldn’t be inferred
->In name to operate ‘decode(_:from:)’ (Basis.JSONDecoder)

58:43 Can not convert worth of sort ‘module’ to anticipated argument sort ‘T.Sort’

108:88 Lacking argument for parameter ‘partei’ in name
->’init(politician:partei:)’ declared right here

My plan was so as to add one other Textual content from the interior construction Partei to my PoliticanDetailView

        Record(viewModel.parteien, id: .parteiID) { partei in
            Textual content("Partei: (partei.namePartei)")

My complete messy code, I’m sorry if it may be not etiquette conform

import SwiftUI

struct Partei: Decodable {
    let parteiID: Int
    let namePartei: String

    non-public enum CodingKeys: String, CodingKey {
        case parteiID = "id"
        case namePartei = "label"
    }
}

struct Politician: Decodable {
    let id: Int
    let firstName: String
    let lastName: String
    let birthYear: Int?
    let beruf: String?
    let geschlecht: String?
    let partei: Partei
    
    enum CodingKeys: String, CodingKey {
        case id
        case firstName = "first_name"
        case lastName = "last_name"
        case birthYear = "year_of_birth"
        case beruf = "occupation"
        case geschlecht = "intercourse"
        case partei
    }
    
}


struct Politicians: Decodable {
    let knowledge: [Politician]
}

actor PoliticianDataService {
    func fetchPoliticians() async throws -> [Politician] {
        guard let url = URL(string: "https://www.abgeordnetenwatch.de/api/v2/politicians") else { return [] }
        
        let (knowledge, _) = attempt await URLSession.shared.knowledge(from: url)
        
        let decoder = JSONDecoder()
        let politicians = attempt decoder.decode(Politicians.self, from: knowledge)
        return politicians.knowledge
    }
}

actor ParteiDataService {
    func fetchParteien() async throws -> [Partei] {
        guard let url = URL(string: "https://www.abgeordnetenwatch.de/api/v2/events") else { return [] }

        let (knowledge, _) = attempt await URLSession.shared.knowledge(from: url)
        
        let decoder = JSONDecoder()
        let parteien = attempt decoder.decode(Parteien.self, from: knowledge)
        return parteien.knowledge
    }
}

@MainActor
class PoliticianListViewModel: ObservableObject {
    @Revealed var politicians = [Politician]()
    
    non-public var dataService = PoliticianDataService()
    
    init() {
        // Extra setup may very well be executed right here if wanted
    }
    
    func fetchPoliticians() {
        Job {
            do {
                let fetchedPoliticians = attempt await dataService.fetchPoliticians()
                politicians = fetchedPoliticians
            } catch {
                print(error)
            }
        }
    }
}

class PoliticianDetailViewModel: ObservableObject {
    @Revealed var parteien = [Partei]()

    non-public var dataService = ParteiDataService()

    func fetchParteien() {
        Job {
            do {
                let fetchedParteien = attempt await dataService.fetchParteien()
                parteien = fetchedParteien
            } catch {
                print(error)
            }
        }
    }
}

struct ContentView: View {
    @StateObject var viewModel = PoliticianListViewModel()
    
    var physique: some View {
        NavigationView {
            Record(viewModel.politicians, id: .id) { politician in
                NavigationLink(vacation spot: PoliticianDetailView(politician: politician)) {
                    Textual content("(politician.firstName) (politician.lastName)")
                }
            }
            .navigationTitle("Politiker in Deutschland")
        }
        .onAppear {
            viewModel.fetchPoliticians()
        }
    }
}

struct PoliticianDetailView: View {
    let politician: Politician
    let partei: Partei
    

    @StateObject non-public var viewModel = PoliticianDetailViewModel()  // Create a ViewModel

    var physique: some View {
        VStack {
            Textual content("Identify: (politician.firstName) (politician.lastName)")
            Textual content("Geburtsjahr (politician.birthYear ?? 0)")
            Textual content("Alter: (calculateAge(birthYear: politician.birthYear ?? 0)) Jahre")
            Textual content("Beschäftigt als (politician.beruf ?? "Unbekannt")")
            Textual content("Geschlecht: (politician.geschlecht ?? "Unbekannt")")

            Record(viewModel.parteien, id: .parteiID) { partei in
                Textual content("Partei: (partei.namePartei)")
            }
            .onAppear {
                viewModel.fetchParteien()
            }
        }
        .navigationTitle("(politician.firstName) (politician.lastName)")
    }

    func calculateAge(birthYear: Int) -> Int {
        let currentYear = Calendar.present.part(.12 months, from: Date())
        return currentYear - birthYear
    }
}

struct ContentView_Previews: PreviewProvider {
    static var previews: some View {
        ContentView()
    }
}

Related Articles

LEAVE A REPLY

Please enter your comment!
Please enter your name here

Latest Articles