2016-09-22 70 views
1

我想在我的項目中創建一個異步方法,它需要一些輸入參數。如果參數是正確的,它會做一些事情,然後調用完成塊。但是,如果輸入參數不正確,那麼它將不會執行這些操作(所以完成塊將不會運行,我必須自己調用它)。Swift異步方法和返回/完成塊

無論如何,我想最好的辦法是什麼這個...

我想我可以有方法返回一個Status枚舉,包括什麼是錯的輸入,然後也有完成塊。

問題是從完成塊也可能有錯誤。所以也許這應該是一個不同的錯誤類型?

就像這樣...(以登錄爲例)。

enum LoginRequestStatus { 
    case missingEmail 
    case missingPassword 
    case requestingLogin 
} 

然後從完成的錯誤可能是......

enum LoginError: Error { 
    case noUserFound 
    case invalidPassword 
    case success 
} 

然後,該功能可能會是這個樣子......

func login(withEmail email: String, password: String, completion: (LoginError?) ->()) -> LoginStatus { 
    if email.isEmpty() { 
     return LoginStatus.missingEmail 
    } 
    if password.isEmpty() { 
     return LoginStatus.missingPassword 
    } 

    //make some async request here or something... 

    //... if error... 
    completion(LoginError.invalidPassword) 

    return LoginStatus.requestingLogin 
} 

這是否有意義?那是Swifty(我討厭那個詞,但它描繪了我的意思)?有什麼不同的方式可以完全解決這個問題嗎?

由於

+0

我想,如果我正確地得到了你的問題,有兩種類型的錯誤,你想要管理。您可以通過在完成塊中設置另一個變量(let int int類型)來管理它,而不使用返回類型。 像是如果錯誤是「LoginRequestStatus」類型傳遞100和其他傳遞101.然後在完成方法檢查如果int值是100那麼它是「LoginRequestStatus」類型或另一個。並據此進行管理。那有意義嗎?? – Janmenjaya

+0

你的方式也沒有錯,使用'throws'也沒有錯,每個方式也都可以用罰,Alamofire使用完成塊和其他一些使用拋出處理錯誤,除此之外,'return LoginStatus'似乎確實不需要,因爲它總是返回'LoginStatus.requestingLogin',調用的目的是什麼? – Tj3n

回答

2

從我的觀點來看,可以使用throws簡化與方法的相互作用。我寫一個小例子。有了這個實現,因爲exceptions,所以不會錯過錯誤。如果請求成功,將顯示清晰的響應狀態。

拋出錯誤:

enum LoginError: ErrorType { 
    case missingEmail 
    case missingPassword 
} 

響應狀態:

enum LoginRequestStatus { 
    case noUserFound 
    case invalidPassword 
    case success 
} 

功能實現:

func login(withEmail email: String, password: String) throws -> LoginRequestStatus { 

    guard email.characters.count > 0 else{ 
     throw LoginError.missingEmail 
    } 

    guard password.characters.count > 0 else{ 
     throw LoginError.missingPassword 
    } 

    // do some request 

    return LoginRequestStatus.success 
} 
+0

謝謝。我將把投擲錯誤和完成塊結合起來。 – Fogmeister