今回は Google アカウントを利用した認証手順について解説します。
前回まで記事については下記をご参照ください。
- ①基本設定編
- ②メールアドレス・パスワード認証によるユーザー登録編
- ③メールアドレス・パスワード認証によるログイン・ログアウト編
- ④メールアドレスとパスワードの更新編
- ⑤メールアドレスの確認メール送信・パスワード再設定メール送信編
- ⑥ユーザーの再認証編
- ⑦Googleアカウントログイン編(本記事)
- ⑧Apple アカウントログイン編
- ⑨ユーザープロフィール更新編
- ⑩匿名ログイン編
Firebase Authentication の iOS 導入手順【⑦Googleアカウントログイン編】【SwiftUI】
(1) Sign in Method で Google ログインを許可する
先ず最初に、Firebase コンソール画面にログインし Google アカウントによるログインを許可する必要があります。
[Authentication] > [Sign-in method] からログインプロバイダの Google を有効化しましょう。保存して、有効になっているか確認してください。
(2) GoogleSignIn を pod install する
vi コマンドで Podfile を開き、Firebase/Auth と GoogleSignIn をインストールするように設定します。
$ vi Podfile
・・・
pod 'Firebase/Auth'
pod 'GoogleSignIn'
pod install でインストールしましょう。
$ pod install
(3) URL Types の設定
Xcode の [Targets] > [Info] > [URL Types] を追加し、URL Scheme に GoogleService-Info.plist の REVERSED_CLIENT_ID を指定します。
(4) GIDSignIn インスタンスの設定
ここからソースコードの方に移ります。
先ず、AppDelegate の didFinishLaunchingWithOptions 内で GIDSignIn のシングルトンインスタンスに対して FirebaseApp のクライアントIDを設定します。
import Firebase
import GoogleSignIn
@UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
FirebaseApp.configure()
GIDSignIn.sharedInstance()?.clientID = FirebaseApp.app()?.options.clientID
return true
}
・・・
}
(4) Google ログインボタンを作成する
Google アカウントのログインを実行するには専用のボタンである GIDSignInButton を用意する必要があります。
これは UIKit 前提のボタンとなっているため、SwiftUI で使う場合は以下のように UIViewControllerRepresentable を継承しラッピングします。
※コード内の GoogleSignInViewController は後述します。
struct GoogleSignInButton: View {
var body: some View {
GoogleSignInButtonViewController()
}
}
struct GoogleSignInButtonViewController: UIViewControllerRepresentable {
func makeUIViewController(context: Context) -> UIViewController {
let gidSignInButton = GIDSignInButton()
gidSignInButton.style = .wide
let viewController = GoogleSignInViewController()
viewController.view.addSubview(gidSignInButton)
return viewController
}
func updateUIViewController(_ uiViewController: UIViewController, context: Context) {
}
}
ボタンをタップするとブラウザが立ち上がり、Google アカウントによるログイン画面が表示されます(ただし、この時点では後述の処理が足りていないためエラーとなってしまいます)。
(5) ブラウザからのログイン結果をキャッチする
ボタンを押して立ち上がるブラウザの処理と連携するために、GIDSignIn インスタンスにデリゲートを設定する必要があります。
これは、UIViewController でなくてはいけないため、GIDSignInDelegate を継承した以下のような ViewController を作成します。
import UIKit
import GoogleSignIn
import FirebaseAuth
class GoogleSignInViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
GIDSignIn.sharedInstance()?.presentingViewController = self
GIDSignIn.sharedInstance()?.delegate = self
}
}
extension GoogleSignInViewController: GIDSignInDelegate {
func sign(_ signIn: GIDSignIn!, didSignInFor user: GIDGoogleUser!, withError error: Error!) {
if let error = error {
print(error.localizedDescription)
return
}
guard let auth = user.authentication else {
return
}
let credential = GoogleAuthProvider.credential(withIDToken: auth.idToken, accessToken: auth.accessToken)
Auth.auth().signIn(with: credential) { authResult, error in
if let error = error {
print(error.localizedDescription)
} else {
print("Google SignIn Success!")
}
}
}
}
ブラウザ側でログイン処理が完了すると、
sign(_ signIn: GIDSignIn!, didSignInFor user: GIDGoogleUser!, withError error: Error!)
がコールされます。
引数の user の情報を使って、GoogleAuthProvider の credential(認証情報)を生成し、それを引数に FirebaseAuth の signIn を実行します。
サインアウトしたい場合は Auth.auth().signOut をコールすればOKです。
signOut はプロバイダの種類を問わないため、メールアドレスとパスワードの時と同じです。
do {
try Auth.auth().signOut()
} catch let signOutError as NSError {
print ("Error signing out: %@", signOutError)
}
以上