Vuexを使用してFirebaseのログイン情報を保持する方法

プログラミング

こんにちは!いっちー(@tetestkake_blog)です。

Vue.jsを使用してアプリケーションを開発している時、ログインデータなどをアプリケーション全体で共有したい時ってありますよね。

そこで今回の記事ではVuexを使用した、Firebaseのログイン情報保持方法に関して解説したいと思います。

Vueは2系を使用したサンプルコードも掲載しているのでそちらもご参照ください。

いっちー
いっちー

Vuexを使用するとアプリケーション全体でデータが共有できて便利です。

※この記事ではFirebaseに関しての詳細な説明は省略しています。以下の記事で解説しているのでよろしかったらご覧ください!

スポンサーリンク

Vuexとは?

Vuexとは、Vue.js用の状態管理用ライブラリです。

状態とは、アプリケーションが保持しているデータのことを指します。

Vuexでデータを管理すると、全てのコンポーネントから保存したデータを参照することが可能になります。

要は、アプリケーション全体で使いまわしたいデータを入れておく箱のようなものです。

例えばログイン情報など、全てのコンポーネントから参照しうるデータを格納する場所として使われます。

コンポーネント間のデータのやり取りはpropsやemitからも可能ですが、より広い範囲でデータをやり取りする時などにはVuexを選択すると良さそうです。

Firebaseのログイン情報をVuexで管理

ここからはコードのサンプルを紹介しながらFirebaseのログイン情報をVuexで保持する方法に関して紹介します。

サンプルではログイン機能を担当するLogin.vue, Logout.vueのコードも追加しましたのでそちらもご覧ください!

src/store.js

Vuexに値を保存する部分を担当するstore.jsを作成します。全体のコードは以下になります。

import Vue from 'vue';
import Vuex from 'vuex';

Vue.use(Vuex);

export default new Vuex.Store({
  state: {
    user: {},
    isLoggedIn: false,
  },
  mutations: {
    onAuthStateChanged(state, user) {
      // firebaseが返したユーザー情報
      state.user = user;
    },
    onUserLoginStatusChanged(state, isLoggedIn) {
      // ログインしているかどうか
      state.isLoggedIn = isLoggedIn;
    }
  },
  getters: {
    user(state) {
      return state.user;
    },
    isLoggedIn(state) {
      return state.isLoggedIn;
    }
  }
});

保存するデータの本体はstateの箇所にて宣言します。初期値はuserには空のオブジェクト、isLoggedInにはfalseを設定しています。

データを保存する部分はmutationsが担当します。

mutationsでは第一引数でVuexの状態(state)を受け取り、第二引数で更新する情報を受け取ります。

gettersはstoreに保存した情報を参照する際に使用します。

直接stateを参照することもできてしまいますが、Vuexのお作法的にはgetterを経由して参照することが推奨されています。

いっちー
いっちー

直接stateを参照しないことでVuexでは値に対する秩序を守っているのですね!

src/main.js

main.jsではstoreをVueインスタンスに渡してあげることで、全体でstoreを使用できるようにします。

import Vue from 'vue';
import App from './App.vue';
import vuetify from './plugins/vuetify';
import router from './router';
import firebase from 'firebase';
import store from './store';

Vue.config.productionTip = false;

const firebaseAuthConfig = {
  apiKey: process.env.VUE_APP_FIREBASE_API_KEY,
  authDomain: process.env.VUE_APP_FIREBASE_AUTH_DOMAIN
};

firebase.initializeApp(firebaseAuthConfig);

new Vue({
  vuetify,
  router,
  store,
  render: h => h(App)
}).$mount('#app');

また今回はfirebaseのinit処理もmain.jsに配置しています。

src/firebaseUtils.js

firebaseUtils.jsでは、firebaseから取得したログイン情報と、ログインしているかどうかのboolの値をstoreに保存します。

import firebase from 'firebase';
import store from './store';

export default {
  onAuthStateChanged() {
    firebase.auth().onAuthStateChanged(u => {
      let user = u ? u : {};
      store.commit('onAuthStateChanged', user);
      store.commit('onUserLoginStatusChanged', user.uid ? true : false);
    });
  }
}

ログイン状態が変化した際の処理であるonAuthStateChanged()にて処理を行います。

ここでは、firebaseのログイン状態が変化したことを検知し、

storeに保存しているuser, isLoggedInの情報を更新しています。

処理的には、

user = user ? user : {};

の部分でuserが存在したらuserを、そうでなければ空オブジェクトをuserに詰めています。

store.commit('onAuthStateChanged', user);

ではstoreのonAuthStateChangedを介してuserの情報を更新し、

store.commit('onUserLoginStatusChanged', user.uid ? true : false);

でログインしているかのboolの情報を更新します。

Login.vue

以下のログインコンポーネントでは、ログインフォームの表示とfirebaseを使用したログインを実装しています。

<template>
  <div>
    <h1>ログイン</h1>
    <v-card
      class="pa-5 ma-auto mt-3"
      width="50%"
    >
      <v-form
        ref="loginForm"
      >
        <v-text-field
          v-model="email"
          label="Email"
          :rules="requiredRule"
          required
        ></v-text-field>
        <v-text-field
          v-model="password"
          :append-icon="showPassword ? 'mdi-eye' : 'mdi-eye-off'"
          label="Password"
          :rules="requiredRule"
          :type="showPassword ? 'text' : 'password'"
          required
          @click:append="showPassword = !showPassword"
        ></v-text-field>
        <v-btn
          @click="login"
        >
          ログイン
        </v-btn>
      </v-form>
    </v-card>
  </div>
</template>

<script>
import firebase from 'firebase';
import firebaseUtils from './../firebaseUtils';

export default {
  name: 'Login',
  data: () => ({
    email: "",
    password: "",
    requiredRule: [
      value => !!value || '必須項目です',
    ],
    showPassword: false,
  }),
  methods: {
    login() {
      if (this.$refs.loginForm.validate()) {
        firebase.auth().signInWithEmailAndPassword(this.email, this.password)
        .then(() => {
          firebaseUtils.onAuthStateChanged();
          alert('login success');
        })
        .catch(e => {
          alert('login error');
          console.log('error', e);
        })
      } else {
        alert('validate error');
      }
    },
  }
}
</script>

ログインに関しての処理は

firebase.auth().signInWithEmailAndPassword(this.email, this.password)

にてフォームから入力されたメールアドレスとパスワードの情報をFirebaseに渡すことでログインを実現し、

firebaseUtils.onAuthStateChanged();

にてstoreに保存しているユーザーの情報を書き換えています。

Logout.vue

以下のログアウトコンポーネントでは、ログアウトボタンの表示とfirebaseを使用したログアウトを実装しています。

<template>
  <v-card
    class="pa-5 ma-auto"
    width="50%"
  >
    <div class="logout">ログアウトしますか?</div>
    <v-btn
      class="ma-3"
      color="gray"
      @click="$router.go(-1)"
    >戻る</v-btn>
    <v-btn
      color="grey lighten-1"
      dark
      @click="logout()"
    >ログアウト</v-btn>
  </v-card>
</template>

<script>
import firebase from 'firebase';
import firebaseUtils from './../firebaseUtils';
import router from '@/router';

export default {
  name: 'Logout',
  methods: {
    logout() {
      firebase.auth().signOut()
      .then(() => {
        firebaseUtils.onAuthStateChanged();
        // ログイン画面に遷移
        router.push({ path: '/login' });
      })
      .catch(() => {
        alert('ログアウト失敗')
      });
    }
  },
}
</script>

<style scoped>
.logout {
  font-size: 40px;
  font-weight: bold;
}
</style>

ログアウトに関しての処理は

firebase.auth().signOut()

にて完結し、それが成功したら

firebaseUtils.onAuthStateChanged();

にてstoreに保存しているユーザーの情報を書き換えています。

いっちー
いっちー

これでログインとログアウト時にVuexに保存しているユーザーの情報を書き換えることに成功しました!

さいごに

今回はVuexを使用してFirebaseのログイン情報を保持する方法というテーマでお伝えしました。

コンポーネント全体でデータを共有する必要がある場合などは、Vuexを使ってみてください。

参考リンク

Vuex 公式ドキュメント

Qiita Vue vuexでfirebaseのログイン保持

おすすめ書籍

改訂2版 基礎から学ぶVue.js

Vue.js入門 基礎から実践アプリケーション開発まで

お知らせ

にほんブログ村のランキングに参加しています。よろしければ下のボタンをポチッとしていただけると嬉しいです\(^^)/

にほんブログ村 IT技術ブログへ
にほんブログ村

コメント

タイトルとURLをコピーしました