ios swift 从未调用过午睡 ResourceObserver resourceRequestProgress

ios swift siesta ResourceObserver resourceRequestProgress never called

我正在使用 Siesta 进行 REST 调用,我正在尝试创建一个简单的 ResourceObserver 来显示 SVProgressHUD。

open class SVProgressHUDResourceObserver: ResourceObserver {
    static let sharedInstance = SVProgressHUDResourceObserver()

    // Show/Hide SVProgressHUD
    public func resourceRequestProgress(for resource: Resource, progress: Double) {
        print("SVProgressHUDResourceObserver resourceRequestProgress - progress=\(progress)")
        if progress == 1 {
            print("SVProgressHUD.dismiss()")
            SVProgressHUD.dismiss()
        } else if !SVProgressHUD.isVisible() {
            print("show()")
            SVProgressHUD.show()
        }
    }

    public func resourceChanged(_ resource: Resource, event: ResourceEvent) {
        print("SVProgressHUDResourceObserver resourceChanged  event=\(event)")
    }
}

由于是单例,我使用弱引用添加了观察者:

@discardableResult func login(_ username: String, _ password: String,
                                  onSuccess: @escaping (LoginResponse) -> Void,
                                  onFailure: @escaping (Int?, String) -> Void) -> Request {
        return service.resource("/app/v1/authentication/login")
            .addObserver(SVProgressHUDResourceObserver.sharedInstance)
            .request(.post, json: [
                "username": username,
                "password": password
                ])
            .onSuccess { entity in
                guard let loginResponse: LoginResponse = entity.typedContent() else {
                    onFailure(0, "JSON parsing error")
                    return
                }
                self.authToken = loginResponse.session.token
                SessionManager.beginNewSession(loginResponse)
                onSuccess(loginResponse)
            }
            .onFailure { (error) in
                onFailure(error.httpStatusCode, error.userMessage)
        }
    }

我故意为登录添加了 10 秒的延迟,但是 SVProgressHUD 从未显示,实际上 resourceRequestProgress 方法从未被调用。身份验证过程非常有效。

日志输出为:

SVProgressHUDResourceObserver resourceChanged  event=observerAdded
SVProgressHUDResourceObserver resourceChanged  event=newData(wipe)

如能提供帮助,我们将不胜感激。

午睡有区别:

  1. 整个资源本身的状态,Siesta 缓存并保留以供任何人观察,并且
  2. 与资源相关的单个请求的结果,Siesta 将其发送到请求挂钩,但在请求被解除分配后最终会被丢弃。

请注意,对于 #1,如果 任何人 更新资源状态,观察者都会收到通知,而对于 #2,只有专门为该请求注册的挂钩才会收到通知。

这两个携带不同类型的信息。 #1 用于更新资源状态的持续共享真相(“当前用户的配置文件”),而#2 用于更新资源上特定 action 的状态(“更改用户密码”)。

花点时间消化用户指南中的“Request vs. Load”。然后,一旦您理解了这一点,请继续阅读。


在此代码中,您将 SVProgressHUDResourceObserver.sharedInstance 作为资源本身的观察者附加:

    return service.resource("/app/v1/authentication/login")
        .addObserver(SVProgressHUDResourceObserver.sharedInstance)

…这意味着它只会收到 load() 请求的通知。但是你从来没有load它;你只request吧:

        .request(.post, json: [
            "username": username,
            "password": password
            ])

…这意味着只有您附加到那个特定请求的请求挂钩(onSuccessonFailure)才会收到通知它已完成。


如果你只需要一个进度条,放弃 ResourceObserver 并使用请求的 onProgress 挂钩。

(如果您需要保存登录结果,则用户指南列出了如何更新资源的状态以响应 post 请求。但是,看起来您已经存储了通过其他方式验证凭据,这是一种典型的好方法。)