SwiftUI Combine URLSession JSON Сетевой вызов - PullRequest
1 голос
/ 09 апреля 2020

Я пытаюсь понять методологию Combine для совершения JSON сетевого вызова. Я явно упускаю что-то из базовых c.

. При ближайшем сбое, полученном при отмене URLSession.

class NoteDataStore: ObservableObject {

    @Published var notes: [MyNote] = []

    init() {
        getWebserviceNotes()
    }

    func getWebserviceNotes() {

        let pub = Webservice().fetchNotes()
            .sink(receiveCompletion: {_ in}, receiveValue: { (notes) in
            self.notes = notes
            })
        }
    }
}//class

Элемент данных:

struct MyNote: Codable, Identifiable {
    let id = UUID()
    var title: String
    var url: String
    var thumbnailUrl: String

    static var placeholder: MyNote {
        return MyNote(title: "No Title", url: "", thumbnailUrl: "")
    }
}

настройка сети:

class Webservice {
    func fetchNotes() -> AnyPublisher<[MyNote], Error> {
        let url = "https://jsonplaceholder.typicode.com/photos"
        guard let notesURL = URL(string: url) else { fatalError("The URL is broken")}

        return URLSession.shared.dataTaskPublisher(for: notesURL)
            .map { $0.data }
            .decode(type: [MyNote].self, decoder: JSONDecoder())
            .receive(on: RunLoop.main)
            .eraseToAnyPublisher()
    }
}

Выход консоли:

Задача <85208F00-BC24-44AA-B644-E0398FE263A6>. <1> завершена с ошибкой [-999] Ошибка Domain = NSURLErrorDomain Code = -999 "отменено" UserInfo = {NSErrorFailingURLStringKey = https://jsonplaceholder.typicode.com/photos, NSLocalizedDescription = отменено, NSErrorFailingURLKey = https://jsonplaceholder.typicode.com/photos}

Любое руководство будет оценено. Xcode 11,4

Ответы [ 2 ]

1 голос
/ 09 апреля 2020
let pub = Webservice().fetchNotes()

этот издатель выпускается при выходе из области видимости, поэтому включите его, как

private var publisher: AnyPublisher<[MyNote], Error>?

func getWebserviceNotes() {
    self.publisher = Webservice().fetchNotes()
    ...
0 голосов
/ 09 апреля 2020

Основываясь на ответе Аспери - вы также захотите добавить:

var cancellable: AnyCancellable?

А затем вы можете получить данные:

func getWebserviceNotes() {

    self.publisher = Webservice().fetchNotes()
    guard let pub = self.publisher else { return }

    cancellable = pub
            .sink(receiveCompletion: {_ in },
                  receiveValue: { (notes) in
                    self.notes = notes
            })
}
...