Can a Swift value be returned from an asynchronous Void return block?

I want to create a function to check if user_id is already in my database.

class func checkIfUserExsits(uid:String) -> Bool { userRef.childByAppendingPath(uid).observeSingleEventOfType(.Value, withBlock: { (snapShot: FDataSnapshot!) -> Void in if snapShot.value is NSNull { return false } else { return true } }) } 

However, observeSingleEventOfType is an API provided by third-party Firebase. It is defined as return Void .

  • (void) observSingleEventOfType: (FEventType) eventType withBlock: (void (^) (FDataSnapshot * snapshot)) block

Error: Type 'Void' does not conform to protocol 'BooleanLiteralConvertible'

Appreciate any kind of help.


UPDATE

I try differently:

 class func checkIfExist(uid: String) -> Bool { var answer:Bool = false var text:String = "not yet completed" let queue = dispatch_group_create() dispatch_group_enter(queue) userRef.childByAppendingPath(uid).observeSingleEventOfType(.Value, withBlock: { (snapShot: FDataSnapshot!) -> Void in if snapShot.value is NSNull { text = "This is a new user" answer = false dispatch_group_leave(queue) } else { text = "Found the user in Firebase" answer = true dispatch_group_leave(queue) } }) dispatch_group_wait(queue, DISPATCH_TIME_FOREVER) println(text) return answer } 

Somehow he just freezes there. I know that this approach may be off topic. But please help.

+7
closures return swift objective-c-blocks firebase
source share
1 answer

You should use an asynchronous completion handler:

 class func checkIfUserExists(uid: String, completionHandler: (Bool) -> ()) { userRef.childByAppendingPath(uid).observeSingleEventOfType(.Value) { snapShot in if snapShot.value is NSNull { completionHandler(false) } else { completionHandler(true) } } } 

Then you can call it like this:

 MyClass.checkIfUserExists(uid) { success in // use success here } // but not here 

In your revised question, you demonstrate the use of send groups so that this asynchronous method works synchronously. (Semaphores are also often used for the same purpose.)

Two questions:

  • This will be inhibited if they send the completion handler to the main queue (and in many cases the libraries will do this to make life easier for us), because you accidentally block the same thread that they are trying to use. I don’t know what they did here, but most likely.

    If you want to confirm this, temporarily delete the submit group and then look at NSThread.isMainThread and see if it works in the main thread or not.

  • In any case, you should never block the main thread. They provided an asynchronous interface for a good reason, so asynchronous templates should be used when calling it. Do not fight with asynchronous patterns, but hug them.

+14
source share

All Articles