PromiseKit 没有回调/解除分配? (阿拉莫菲尔)

Posted

技术标签:

【中文标题】PromiseKit 没有回调/解除分配? (阿拉莫菲尔)【英文标题】:PromiseKit no callback / deallocates? (Alamofire) 【发布时间】:2019-12-13 12:58:59 【问题描述】:

我的承诺链在解决之前就被破坏了(可能被解除分配)。 当我因主机信任评估而使 Alamofire 请求失败时(目前仅)会发生这种情况 -> 强制评估失败导致 -999 被取消等)。

设置相当简单:

API请求:

func start(_ onSuccess:@escaping SuccessBlock, onError:@escaping ErrorBlock) 

    do 
        try executeRequest  dataResponse in
            self.onSuccess(dataResponse)
        

     catch 
        self.onError(error)
    

其中 executeRequest() 是:

self.manager.request(request).responseJSON(queue: self.queue)  (response) in

    completion(response)


然后,定义为 APIRequest 扩展的 PromiseKit 包装器: (无论哪种情况,这个包装回调都被正确调用)

func start() -> Promise<APIResponse> 

    return Promise<APIResponse>  resolver in

        self.start( response in

            resolver.fulfill(response)

        )  error in

            resolver.reject(error)
        
    


最后,单元测试调用启动承诺(扩展): (如果 Alamofire 失败,流量永远不会到达这个地方)

request.start().done  response in

.catch  error in
    // not called if request failed


结果:如果请求失败 -> 扩展承诺包装器(捕获)块被调用,但它没有传播回 UnitTest 承诺块。

只需用模拟实现替换 Alamofire 请求(这会触发一些其他错误(使所有设置按预期工作(单元测试完成并调用 catch 块等)例如:

DispatchQueue.global(qos: .default).asyncAfter(deadline: .now() + 2) 
    let result = Alamofire.Result  () -> Any in 
       return try JSONSerialization.data(withJSONObject: [:], options: .fragmentsAllowed)
  
  completion(DataResponse<Any>(request: nil, response: nil, data: nil, result: result))

这和 Alamofire 有关吗?我真的不知道如何处理那里的承诺(无论如何它们都不应该解除分配......或者PromiseKit中的这个错误?Alamofire?我还必须在应用程序本身中测试它(也许它是单元测试问题.. .)

查看相关问题 -> 我肯定会解决任何流程路径的承诺(履行/拒绝)。

我看不出 Alamofire 请求与 DispatchAsync 有何不同(后者按预期工作)。

【问题讨论】:

【参考方案1】:

我只差 10 分钟就能找到答案……这里也描述了问题: https://github.com/mxcl/PromiseKit/issues/686

问题是 PromiseKit 不会将“-999 cancelled”错误视为“错误”。解决方案是使用“catch(policy: .allErrors)” - 然后按预期调用 catch 块。

【讨论】:

【参考方案2】:
func start(_ onSuccess:@escaping SuccessBlock, onError:@escaping ErrorBlock) 

    do 
        try executeRequest  dataResponse in
            onSuccess(dataResponse)
        

     catch 
        onError(error)
    

您正在使用 self.onSuccess,这意味着它不是函数参数块而是实例块,这就是为什么它不会从您调用 start 时返回块。

【讨论】:

我在上面确实说过完成块被正确调用。我发布的代码已简化,因此如果造成混淆,请接受我的歉意。 好,我关注这个语句结果:如果请求失败 -> 扩展承诺包装器(捕获)块被调用,但它没有传播回 UnitTest 承诺块。

以上是关于PromiseKit 没有回调/解除分配? (阿拉莫菲尔)的主要内容,如果未能解决你的问题,请参考以下文章

PromiseKit 无法将类型 '[Result<TYPE>]' 的值分配给类型 '[TYPE]

如何在没有委托的情况下以模态方式呈现 ViewController,然后在 ViewController 被解除后运行回调函数/块?

PromiseKit 3.0:用循环链接

Xcode中奇怪的promiseKit 6语法行为

如何使用 PromiseKit 在 Swift 3 中手动触发 Promise

根据标记和当前电源状态解除分配 Azure VMSS