👋

サインアップ画面を作成してみた

に公開

関連記事

https://zenn.dev/shunsuke_stack/articles/3b7759f0053ca6

https://zenn.dev/shunsuke_stack/articles/bdf5b784bd6f8b

GitHub

https://github.com/nakajima-sh-cnctor/nuxt4-firebase-chat

画面の完成系

docs

  • ログインのテキストボタンはログイン画面に戻る
  • 入力項目に関してはユーザ認証コンポーネントを活用
  • パスワードの入力に6文字以上のバリデーションを追加
  • サインアップ完了の際はログイン画面に遷移する

FirebaseのcreateUserWithEmailAndPasswordメソッドについて

createUserWithEmailAndPasswordは、Firebase Authenticationが提供する、Eメールアドレスとパスワードを使って新しいユーザーアカウントを作成するための基本的な機能です。このメソッドを呼び出すと、Firebaseは裏側で新しいユーザーID(UID)を生成し、提供されたEメールとハッシュ化されたパスワードをFirebaseプロジェクトに安全に保存します。

主にウェブアプリケーション(JavaScript)やモバイルアプリ(iOS/Android)で、新規ユーザー登録機能を実装する際に利用されます。


主な機能と仕組み

createUserWithEmailAndPasswordの主な役割はシンプルです。

  • 入力: Eメールアドレスとパスワードの2つの文字列を受け取ります。
  • 処理: Firebaseのバックエンドで以下の処理を実行します。
    1. Eメールアドレスの形式が正しいか検証します。
    2. そのEメールアドレスが既に登録されていないか確認します。
    3. パスワードがFirebaseプロジェクトで設定されたセキュリティ要件(デフォルトでは6文字以上)を満たしているかチェックします。
    4. 全てのチェックを通過すると、新しいユーザーアカウントを作成し、データベースに保存します。
  • 出力:
    • 成功時: UserCredential オブジェクトを返します。このオブジェクトには、新しく作成されたユーザーの情報(userオブジェクト)が含まれており、user.uidのようにしてユーザー固有のIDにアクセスできます。ユーザーは自動的にログイン状態になります。
    • 失敗時: エラーオブジェクトを返します。例えば、メールアドレスが既に使用されている場合や、パスワードが脆弱な場合など、原因に応じたエラーコードが含まれています。

コードのポイント

  1. getAuth(): まず、Firebase Authenticationのサービスインスタンスを取得します。
  2. createUserWithEmailAndPassword(): authインスタンス、Eメール、パスワードを引数として呼び出します。この関数はPromiseを返すため、.then()で成功時の処理、.catch()で失敗時の処理を記述します。
  3. 成功時の処理: thenブロックでは、引数としてuserCredentialオブジェクトが渡されます。ここからuserオブジェクトを取得し、UIDなどを利用できます。
  4. エラーハンドリング: catchブロックでは、errorオブジェクトを受け取ります。error.codeを確認することで、エラーの原因を特定し、ユーザーに分かりやすいメッセージを表示することが重要です。

主なエラーコード

開発時によく遭遇する代表的なエラーコードは以下の通りです。

エラーコード 意味 対処法
auth/email-already-in-use 指定されたEメールアドレスが既に使用されている。 ユーザーに別のメールアドレスを使用するか、パスワードリセットを促す。
auth/invalid-email Eメールアドレスの形式が正しくない。 ユーザーに入力内容の確認を促す。
auth/weak-password パスワードが脆弱すぎる(デフォルトでは6文字未満)。 パスワードの要件(例:6文字以上)をユーザーに伝える。
auth/operation-not-allowed FirebaseプロジェクトでEメール/パスワード認証が有効になっていない。 FirebaseコンソールのAuthentication設定で、Eメール/パスワードサインインプロバイダを有効にする。

これらのエラーコードを適切にハンドリングすることで、ユーザーにとって親切な登録フォームを作成することができます。

実際のコード紹介

app/pages/signup.vue
<template>
  <v-card class="mx-auto my-8" max-width="400">
    <v-card-item>
      <v-card-title> サインアップ </v-card-title>
      <v-card-subtitle>
        Firebaseによる”メールアドレス/パスワード”を登録を行う
      </v-card-subtitle>
    </v-card-item>
    <v-card-item>
      <v-btn
        variant="text"
        color="primary"
        class="ma-0 pa-0"
        @click="navigateTo('/login')"
      >
        ログイン
      </v-btn>
      <v-alert
        v-if="error"
        type="error"
        :text="error"
        variant="tonal"
      ></v-alert>
      <AuthForm
        class="my-4"
        btn-label="サインアップ"
        :loading="loading"
        @submit="signupSubmit"
      />
    </v-card-item>
  </v-card>
</template>

<script setup lang="ts">
import AuthForm from '~/components/AuthForm.vue'

const { signup, loading } = useAuth()

const error = ref('')

const signupSubmit = async (data: { email: string; password: string }) => {
  error.value = ''
  const result = await signup(data.email, data.password)

  if (result.error) {
    error.value = result.error.message
  } else {
    // ログイン成功時にindexページに遷移
    await navigateTo('/login')
  }
}
</script>

app/composables/useAuth.ts
...中略
  // サインアップ
  const signup = async (email: string, password: string) => {
    loading.value = true
    if (!auth) {
      return {
        user: null,
        error: new Error('Firebase認証が初期化されていません'),
      }
    }
    try {
      const userCredential = await createUserWithEmailAndPassword(
        auth,
        email,
        password
      )
      return { user: userCredential.user, error: null }
    } catch (error) {
      return { user: null, error: error as Error }
    } finally {
      loading.value = false
    }
  }
...中略

loading関連の値はcomposablesのuseAuthで管理している所がポイント
昔の自分ならloadingの値をVueファイルで管理してました。

GitHubで編集を提案

Discussion