Swiftの { }内の処理の流れが分かりません。


下のコードの  
`signIn(withEmail:link:)`メソッドの`{}`内の処理の流れがよく分かりません。  
`self.hideSpinner{}`は必ず実行されるのしょうか？  
このような構文は何と呼ばれるものですか？

[code]

    if let email = self.emailField.text {
        showSpinner {
            // [START signin_emaillink]
            Auth.auth().signIn(withEmail: email, link: self.link) { (user, error) in
                // [START_EXCLUDE]
                self.hideSpinner {
                    if let error = error {
                        self.showMessagePrompt(error.localizedDescription)
                            return
                    }
                    self.navigationController!.popViewController(animated: true)
                }
                // [END_EXCLUDE]
            }
            // [END signin_emaillink]
        }
    } else {
        self.showMessagePrompt("Email can't be empty")
    }
    
[/code]




メソッド呼び出しの後ろについている `{ ... }` は クロージャ (Closure) と呼ばれるものです。  
`signIn(withEmail:link:)` だけではなく、 `showSpinner` や `hideSpinner` にくっついている `{
... }` もクロージャです。

クロージャは関数のようなものですが、クロージャ自体を変数に入れたり、他のメソッドや関数に渡したり、戻り値として返したりすることができます。

簡単な例を上げると以下のようになります

[code]

    // "ABC"をプリントするクロージャ
    let c1 = {
        print("ABC")
    }
    c1() // ABC と表示される
    
    // 与えられた整数を2倍にするクロージャ
    let c2 = {
        (a:Int) -> Int in
        return a * 2
    }
    c2(2) // 4が返される
    
    // クロージャを引数に受け取る関数
    // 与えられたクロージャを二回呼び出す
    func f1(closure: ()->Void) {
        closure()
        closure()
    }
    
    // "ABC"が二回プリントされる
    f1(closure: c1)
    
    // 関数の最後の引数がクロージャの場合、関数の後ろに { } をくっつけて書くことができる
    f1 {
        print("Yeah!")
    }
    
[/code]

これを踏まえると

> self.hideSpinner{}は必ず実行されるのしょうか？

は **`signIn(withEmail:link:)` の実装や処理結果による**

が回答になります。  
メソッド名からは、サインインが成功したら `user`、失敗したら `error`
に値を入れて、クロージャが呼び出されるのではないかと期待しますが、本当にそうかは分かりません。  
(実装やAPI仕様を確認したり、実際に実行して試してみたりすれば分かるでしょう)

**追記**

forestさんの過去の質問から、おそらくSwiftよりJavaScriptの方が詳しいのかと思います。  
なので元のプログラムをJavaScript風に翻訳してみましょう。以下のようになります。

[code]

    this.showSpinner(function() {
        // [START signin_emaillink]
        Auth.auth().signInWithEmail(email, this.link, function(user, error){
            // [START_EXCLUDE]
            this.hideSpinner( function() {
                if (error) {
                    this.showMessagePrompt(error.localizedDescription);
                    return;
                }
                this.navigationController.popViewControllerAnimated(true);
            });
            // [END_EXCLUDE]
        });
        // [END signin_emaillink]
    });
    
[/code]

つまり、Swiftのクロージャ `{ ... }` はJavaScriptの無名functionと同じでものです。  
無名functionはメソッドの引数として、それぞれ `showSpinner`, `hideSpinner`, `signIn`
という別のメソッドに渡されていることも分かると思います。渡されたfunctionをどう扱うかはそれぞれのメソッドによります。

