【问题标题】:How to abstract network model fetching如何抽象网络模型获取
【发布时间】:2019-08-26 07:56:27
【问题描述】:

我没有将网络模型加载到每个控制器中,而是尝试将其抽象到一个控制器中ModelLoader

这是我到目前为止的想法:

protocol ModelLoaderDelegate: class {
    func didFetch(model: Any)
    func modelFailedToFetch(errorMessage: String)
}

final class ModelLoader<ModelType> {

    let api: API
    weak var delegate: ModelLoaderDelegate?
    private let client = dependencies.client

    init(api: API) {
        self.api = api
    }

    func fetchModel() {
        client.performRequest(api: api, decodeTo: ModelType.self, completion: { result in
            switch result {
            case .success(let value):
                self.delegate?.didFetch(model: value)
            case .failure(let error):
                self.delegate?.modelFailedToFetch(errorMessage: error.localizedDescription)
            }
        })
    }
}

到目前为止,我无法做的一件事是将ModelLoaderDelegatedidFetch 方法中的Any 替换为类似泛型的参数。

我试着这样做:

func didFetch<T>(info: T)

但在委托的实现者中:

func didFetch<T>(info: T) {
 // I need a concerete type here not a generic
}

找不到其他方法。

【问题讨论】:

  • 那么,您想使用ModelLoader 的多个实例和delegate 的一个实例?
  • @Kamran No. 两者的倍数。

标签: ios swift generics swift-protocols


【解决方案1】:

您可以通过闭包来创建逻辑,而不是通过委托来执行此操作:

final class ModelLoader<ModelType> {

    let api: API
    private let client = dependencies.client

    init(api: API) {
        self.api = api
    }

    func fetchModel<ModelType>(completion: @escaping (Result<ModelType, Error>) -> ()) {
        client.performRequest(api: api, decodeTo: ModelType.self, completion: { result in
            switch result {
            case .success(let value):
                completion(.success(value))
            case .failure(let error):
                completion(.failure(error))
            }
        })
    }
}

我认为使用这种方法会更容易处理响应:)

【讨论】:

  • 谢谢。这是一个很好的方法,但我认为将结果处理从 modelLoader 移动到 viewController 是不值得的。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2010-11-29
  • 2022-08-20
  • 2020-07-20
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多