11
11

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

[Firebase 101] サーバ側の実装不要! Firebaseの認証機能を使ってみる

Last updated at Posted at 2018-05-11

TL;DR

Firebaseの認証機能をつかったシンプルなウェブアプリを作って、Firebase上に公開するまでの流れを説明します。

一度使い方をマスターすれば、驚くようなスピードで認証機能を追加できるようになります。
メールアドレスとパスワードでの認証に加え、ソーシャルIDプロバイダと連携した認証方法がわかります。
この記事で作成したサンプルアプリはこちらから。

この記事を読む前に こちらの動画 に目を通しておくとより理解が深まります。

Firebaseをご存知でない方は こちら をご覧ください。

読者ターゲット

  • フロントエンド開発者でFirebaseに入門してみたい方。
  • Firebaseを使った開発のメンタルモデルを作りたい方。
  • サーバサイドの実装の手間を省きたい方。
  • クラウドの設定が複雑すぎて嫌になってしまいそうな方。
  • Firebaseで静的なコンテンツを公開してみたい方。
  • [IMPORTANT] Firebase初心者の記事でも気にならない寛大な方。

もくじ

  • Firebase Authenticationの簡単な説明
  • Firebaseを使った開発の流れ
  • 参考文献の紹介
  • さらなる話題

Firebase Authenticationの簡単な説明

  • メールアドレスとパスワードによる認証ができます。
  • GoogleやFacebookといったソーシャルIDプロバイダとの連携による認証もできます。
  • フロントエンドの実装だけでユーザ認証機能が作れます。
  • サーバサイドのアプリとも連携させることもできます。

Firebaseを使った開発の流れ

大まかな作業の流れ(3回ほど読んでください)

プロジェクトの準備(Firebase CLIツールのインストール)

アプリケーションのひな型づくり

Firebaseコンソールで新規プロジェクトを作成する

アプリのひな型にFirebaseを組み込む(スニペットの貼り付け)

アプリに認証機能を実装する

Firebaseコンソールで認証機能を有効にする

デプロイ(コマンド一発)

プロジェクトの準備とコマンドラインツールの導入

> mkdir myproject
> cd myproject
> npm init
... 

> npm install --save-dev firebase-tools # firebase CLIのインストール

> $(npm bin)/firebase --version
3.18.4

> $(npm bin)/firebase login             # ブラウザでログイン画面が表示されるので、Firebaseにログインしてください。
> $(npm bin)/firebase init              # Firebaseプロジェクトの初期設定を対話形式で行います。

> mkdir public                          # 外部公開用のディレクトリ
> touch public/index.html               # アプリ本体をここに実装していきます)

firebase initコマンドの詳細は この動画をご覧ください(日本語字幕あり)。

別のGoogleアカウントに切り替えたい場合は、firebase logout コマンドを実行し、再度ログインしなおしてください。

アプリケーションのひな型を作成する

<!DOCTYPE html>
<html>
  <body>
    <div id="auth-logged-out">
      <input id="email" type="email">
      <input id="password" type="password">
      <button id="signup">ユーザ登録</button>
      <button id="login">ログイン</button>
      <button id="google-login">Googleログイン</button>
    </div>
    <div id="auth-logged-in" style="display:none;">
      <p>ログインしました。</p>
      <button id="logout">ログアウト</button>
    </div>

    <!-- のちほど **ここにFirebaseのスニペット** を貼り付けます -->

  </body>
</html>

Firebaseコンソールでのプロジェクトを作成する

Firebaseコンソールを開き、画面の指示に従って新しいプロジェクトを追加します。

create-project.png

プロジェクト名を入力し プロジェクトを作成 ボタンをクリックします。
add-project.png

プロジェクトとアプリを紐づける

webapp.png

Firebaseの組み込み

<button id="google-login">Googleログイン</button>

<script src="https://www.gstatic.com/firebasejs/5.0.2/firebase.js"></script>
<script>
  // Initialize Firebase
  var config = {
    apiKey: "",
    authDomain: "",
    databaseURL: "",
    projectId: "",
    storageBucket: "",
    messagingSenderId: ""
  };
  firebase.initializeApp(config);
</script>

</body>

メールアドレスとパスワードによるサインアップ機能を追加する

// Firebase認証機能はこの値を通して利用します。
const auth = firebase.auth()

// 登録ボタンのイベント登録
document.querySelector('#signup')
  .addEventListener('click', async ev => {
    try {
      await auth
        .createUserWithEmailAndPassword(...getEmailAndPassword())
    } catch (e) {
      console.log('登録失敗', e)
    }
  })

メールアドレスとパスワードによるログイン機能を追加する

// ログインボタンのイベント登録
document.querySelector('#login')
  .addEventListener('click', async ev => {
    try {
      await auth
        .signInWithEmailAndPassword(...getEmailAndPassword())
    } catch(e) {
      console.log('ログイン失敗', e)
    }
  })

Firebaseコンソールでメールアドレスとパスワードによる認証を有効にする

console-auth.ppng.png

auth-mailpass.png

ログアウト機能を追加する

// ログアウトボタンのイベント登録
document.querySelector('#logout')
  .addEventListener('click', () =>
    auth.signOut())

認証状態を監視する

ユーザがFirebaseからログアウトした場合など、ユーザの認証状態に変化が生じた場合の処理を定義します。
ここでは、ログイン中ならばコンテンツを表示します。
そうでないならば、コンテンツを非表示にしログインフォームを表示します。

// 認証状態を監視
auth.onAuthStateChanged(user => {
  if (user) showContents()
  else hideContents()
})

GoogleIDによるログイン機能を追加する

ソーシャルIDプロバイダと連携する場合には、各プロバイダごとに専用に用意された手続をします。
ここでは、Googleにログインするために GoogleAuthProvider を使用しています。
signInWithRedirect はモバイル用のページと相性が良いです。
OAuthをポップアップウィンドウから利用する場合には、 signInWithPopup を利用します。

// Googleログインボタンのイベント登録
document.querySelector('#google-login')
  .addEventListener('click', async () => {
    const provider = new firebase.auth.GoogleAuthProvider()
    provider.addScope('profile')
    try {
      await auth.signInWithRedirect(provider)
    } catch(e) {
      console.log('ログイン失敗', e)
    }
  })

Firebaseコンソールの認証設定画面でGoogleでログインできるように設定を変更する。

こちらと同様の手続きを行ってください。


Firebase Hostingへデプロイする

次のコマンドを実行するとファイルがFirebase Hostingへデプロイされ、公開用URLが表示されます。

> $(npm bin)/firebase deploy

ユーザデータをエクスポートする

次のコマンドを実行すると、Firebase上のユーザデータをローカルホストに保存することができます。
ファイルの形式はJSONまたはCSVが選択できます。
$(npm bin)/firebase auth:export 出力ファイル名 --format=[json|csv]

参考文献の紹介

  • 公式ビデオ

    • まずはこのシリーズを見ましょう。日本語字幕あり。
      Firebaseを使った開発の流れがわかります。
      Reactなどのフレームワークとの連携方法などの説明もあります。
  • 公式ドキュメント

    • ↑のビデオを見たら、公式ドキュメントで認証機能の詳しい説明を見ましょう。
      データベース機能などFirebaseが提供するさまざまなサービス
  • 認証APIリファレンス(ウェブアプリ版)

さらなる話題

  • サーバ側のアプリでFirebaseを使う(Firebase Admin SDK)
  • データベースを使ってみる
  • インスタンス不要! Cloud Functionsを使ったサーバ側ロジックの実装

index.html の全容

<!DOCTYPE html>
<html>
  <body>
    <div id="auth-logged-out">
      <input id="email" type="email" placeholder="nouris@example.com">
      <input id="password" type="password" placeholder="password">
      <button id="signup">ユーザ登録</button>
      <button id="login">ログイン</button>
      <button id="google-login">Googleログイン</button>
    </div>
    <div id="auth-logged-in" style="display:none;">
      <p>ログインしました。</p>
      <button id="logout">ログアウト</button>
    </div>
    <script src="https://www.gstatic.com/firebasejs/5.0.2/firebase.js"></script>
    <script>
    !function(){

      // Initialize Firebase
      var config = {
        apiKey: "",
        authDomain: "",
        databaseURL: "",
        projectId: "",
        storageBucket: "",
        messagingSenderId: ""
      };
      firebase.initializeApp(config);

      // Firebase認証機能はこの値を通して利用します。
      const auth = firebase.auth()

      // 登録ボタンのイベント登録
      document.querySelector('#signup')
        .addEventListener('click', async ev => {
          try {
            await auth
              .createUserWithEmailAndPassword(...getEmailAndPassword())
          } catch (e) {
            console.log('登録失敗', e)
          }
        })

      // ログインボタンのイベント登録
      document.querySelector('#login')
        .addEventListener('click', async ev => {
          try {
            await auth
              .signInWithEmailAndPassword(...getEmailAndPassword())
          } catch(e) {
            console.log('ログイン失敗', e)
          }
        })

      // Googleログインボタンのイベント登録
      document.querySelector('#google-login')
        .addEventListener('click', async () => {
          const provider = new firebase.auth.GoogleAuthProvider()
          provider.addScope('profile')
          try {
            await auth.signInWithRedirect(provider)
          } catch(e) {
            console.log('ログイン失敗', e)
          }
        })

      // ログアウトボタンのイベント登録
      document.querySelector('#logout')
        .addEventListener('click', () =>
          auth.signOut())

      // 認証状態を監視
      auth.onAuthStateChanged(user => {
        if (user) showContents()
        else hideContents()
      })

      function getEmailAndPassword() {
        const email = document.querySelector('#email').value
        const password = document.querySelector('#password').value
        return [email, password]
      }

      function showContents() {
        document.querySelector('#auth-logged-out').style.display = 'none'
        document.querySelector('#auth-logged-in').style.display = 'block'
      }

      function hideContents() {
        document.querySelector('#auth-logged-out').style.display = 'block'
        document.querySelector('#auth-logged-in').style.display = 'none'
      }

    }() // IIFE
    </script>
  </body>
</html>

11
11
2

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
11
11

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?