今回の記事では、JavascriptやFIREBASEの初心者の方や、未経験からエンジニア転職を目指している方向けに、ログインユーザー認証機能の作成方法を解説していきます。
初心者の方にとってちょうど良い練習で、自作したポートフォリオへのアップグレード・追加機能なりますので、ぜひご参考ください。
ユーザ認証機能をつけるアプリは、別の記事で作成したToDoリストに追加していきます。(Todoリストにはあまり必要ない機能ですが、練習として実装していきます。)
ToDoリストの作成方法については、以下の記事を参考ください。
実装の流れ
ToDoリストへのログイン/サインアップ機能の追加の大きな流れは以下になります。
ポイントは、FIREBASEで発行される認証情報をデータベースへのアクセス時に、認証情報を付加してあげる点です。
上記の流れ、各パートを解説していきます。
FIREBASEのデータベースのルールを変更する
FIREBASEのRealtime Databaseのコンソールより「ルール」画面に移動します。現状は、「true」の設定となっており、誰でもデータベースへアクセスできる状態です。
今回は、ログインユーザのみがデータベースの書き込みができるよう変更しますので、write部分を「”auth!=null」にルール変更します。
これでログインしてないユーザはToDoリストの追加・削除ができなくなりました。
FIREBASEの認証機能を有効化する
FIREBASEのサイドメニューから「Authentication」コンソールに移動して、「Sign-in method」を選択します。今回は、メール/パスワードでの認証機能を有効化していきます。
メール/パスワードの有効化にチェックを入れると、以下の画面で有効のステータスに変更されます。
これで、FIREBASE側の設定は完了です。
現時点では、未ログイン状態でリスト追加しようとすると、コンソールにエラーが発生します。
ログイン/サインアップ画面を作成する
続いて、ToDoリスト画面にHTMLとCSSでログイン/サインアップエリアを追加していきます。
HTMLの解説
既に作成済みのToDoリスト部分は割愛し、ログイン/サインアップ部分のみの解説です。
<!-- ログイン/サインアップエリア -->
<div id="auth" class="card">
<h2 id="auth-title">ログイン</h2>
<button id="auth-btn">ログイン</button>
<button id="switch-btn">サインアップ</button><br><br>
<div class="auth-box">
<label for="email">メールアドレス</label>
<input type="email" id="email" placeholder="example@example.com"/>
<label for="password">パスワード</label>
<input type="password" id="password" placeholder="・・・・・・"/>
</div><br><br>
</div>
各ボタンには、Javascriptのイベント実行を後ほど付与していきます。
id=”auth-btn”では、FIREBASE側との認証イベントを付与し、id=”switch-btn”では、ログイン/サインアップの切替イベントを付与します。
メールアドレスとパスワードを取得する入力欄も作成します。
CSSの解説
CSSも認証機能部分のみの解説になります。
/* ユーザ認証機能 */
.hidden{
display: none;
}
.auth-box {
display: flex;
flex-wrap: wrap;
justify-content: space-between;
}
.auth-box input{
margin-top: 15px;
}
.auth-box label{
width: 35%;
margin-top: 15px;
}
#switch-btn{
background-color: white;
color: #333;
}
#switch-btn:hover{
background-color: #d8d8d8;
color: #333;
}
ポイントは、hiddenクラスにdisplay: none;を設定し、ログイン後は、ログインエリアを画面に表示させないように、のちほどJavascript側でクラスの切替を行います。
画面イメージ
HTML、CSS記述後の画面イメージは以下になります。ToDoリストの追加エリアは、ログイン後に表示されるようにしています。
Javascriptで認証処理イベントを作成する
Javascriptも、ユーザ認証機能部分のみの解説になるため、ToDoリスト部分の実装については、冒頭に紹介した記事をご参考ください。
コードの全体像
// ユーザ認証==============
//=========================
//=========================
// ログイン機能追加
const $create = document.querySelector('#create') //リスト追加エリア
const $auth = document.querySelector('#auth') //ログインエリア
const $authTitle = document.querySelector('#auth-title') //ログインエリアタイトル
const $email = document.querySelector('#email') //emailインプット
const $password = document.querySelector('#password') //passwordインプットボックス
const $authBtn = document.querySelector('#auth-btn') //認証イベントボタン
const $switchBtn = document.querySelector('#switch-btn') //切替ボタン
let token; //認証後のtokenを格納する
// サインアップとログインの切り替えイベント
$switchBtn.addEventListener('click',()=>{
if($switchBtn.innerHTML=='サインアップ'){
$authTitle.innerHTML='サインアップ'
$authBtn.innerHTML='サインアップ'
$switchBtn.innerHTML='ログイン'
}else{
$authTitle.innerHTML='ログイン'
$authBtn.innerHTML='ログイン'
$switchBtn.innerHTML='サインアップ'
}
})
// FIREBASEへの接続URL設定と認証メソッドを実行する
$authBtn.addEventListener('click',()=>{
let url ='https://identitytoolkit.googleapis.com/v1/accounts:signInWithPassword?key=AIzaSyB0WZn0qhjc8V1Q17vxCJtdF0kcpEeU364';
if($authBtn.innerHTML=='サインアップ'){
url='https://identitytoolkit.googleapis.com/v1/accounts:signUp?key=AIzaSyB0WZn0qhjc8V1Q17vxCJtdF0kcpEeU364'
}
auth(url); //URLを引数に認証メソッドを実行する
})
// 認証メソッド
async function auth(url){
const response = await fetch(url,{
method:'POST',
body:JSON.stringify({
email:$email.value.trim(),
password:$password.value.trim()
})
});
const responseData = await response.json() //戻り値をJSONへ変換
token=responseData.idToken; //token変数にFIREBASEからのtokenを代入
if(!response.ok){
alert('認証に失敗しました')
return;
}
alert('認証に成功しました')
//hiddenクラスで各エリアの表示・非表示切替
$auth.classList.add('hidden')
$create.classList.remove('hidden')
$btnDelete.classList.remove('hidden')
}
ポイントは、FIREBASEのユーザ認証アクセスが成功した場合、戻り値のトークンを変数に格納し、データベース接続時に使用する点です。
それでは各パートについて、解説していきます。
HTMLの要素(DOM)を取得する
HTMLでマークアップした各要素(DOM)を取得して定数へ定義していきます。
// HTML要素取得
const $create = document.querySelector('#create') //リスト追加エリア
const $auth = document.querySelector('#auth') //ログインエリア
const $authTitle = document.querySelector('#auth-title') //ログインエリアタイトル
const $email = document.querySelector('#email') //emailインプット
const $password = document.querySelector('#password') //passwordインプットボックス
const $authBtn = document.querySelector('#auth-btn') //認証イベントボタン
const $switchBtn = document.querySelector('#switch-btn') //切替ボタン
let token; //認証後のtokenを格納する
9行目のtokenはユーザ認証時のFIREBASEからの戻り値「idToken」を格納し、後ほどデータ取得時に使用します。
ログイン/サインアップを切り替える
HTML上のログイン認証エリアについて、タイトル及びボタンの名称を切り替えます。
// サインアップとログインの切り替えイベント
$switchBtn.addEventListener('click',()=>{
if($switchBtn.innerHTML=='サインアップ'){
$authTitle.innerHTML='サインアップ'
$authBtn.innerHTML='サインアップ'
$switchBtn.innerHTML='ログイン'
}else{
$authTitle.innerHTML='ログイン'
$authBtn.innerHTML='ログイン'
$switchBtn.innerHTML='サインアップ'
}
})
switchボタンがクリックされた時にブラウザの切替イベントを実行します。
if文で、サインアップの状態でswitchボタンがクリックされたら、ログインに切替え、ログイン状態の場合は、サインアップに切替えます。
FIREBASEへの認証用アクセスURLを設定する
FIREBASEのユーザ認証用URLを定義して、認証用のメソッドを実行します。
// FIREBASEへの接続URL設定と認証メソッドを実行する
$authBtn.addEventListener('click',()=>{
let url ='https://identitytoolkit.googleapis.com/v1/accounts:signInWithPassword?key=ご自身のAPIキー';
if($authBtn.innerHTML=='サインアップ'){
url='https://identitytoolkit.googleapis.com/v1/accounts:signUp?key=ご自身のAPIキー'
}
auth(url); //URLを引数に認証メソッドを実行する
})
サインアップとログインで、URLが異なりますので、4行目~のif文でボタンの状態を確認して、URLを切り替えます。
URLを引数に、認証メソッドを実行します。(認証メソッドは後述します)
認証用アクセスURLを確認する
認証用のアクセスURLは、FIREBASEの公式ドキュメントから確認できます。
今回は、「メール/パスワードでサインアップ」と「メール/パスワードでサインアップ」を確認し、エンドポイントのURLを使用します。
末尾の[API_KEY]は、自身のFIREBASEのWebAPIキーになります。
WebAPIキーを確認する
WebAPIキーは、FIREBASEコンソールの「プロジェクトの設定」から確認できます。
「ウェブAPIキー」の欄にご自身のキーが載っています。
認証メソッドを実行する
先ほど確認したURLを引数にFIREBASEと通信する、認証メソッドを実行します。
// 認証メソッド
async function auth(url){
const response = await fetch(url,{
method:'POST',
body:JSON.stringify({
email:$email.value.trim(),
password:$password.value.trim()
})
});
const responseData = await response.json() //戻り値をJSONへ変換
token=responseData.idToken; //token変数にFIREBASEからのtokenを代入
if(!response.ok){
alert('認証に失敗しました')
return;
}
alert('認証に成功しました')
//hiddenクラスで各エリアの表示・非表示切替
$auth.classList.add('hidden')
$create.classList.remove('hidden')
$btnDelete.classList.remove('hidden')
}
- 3行目~:URLを設定して、FIREBASEとfetch通信します。メソッドはPOSTで、ボディーには、インプットボックスの入力値を設定します。
- 11行目:fetch通信の戻り値「idToken」を「token」へ格納します。
- 12行目~:認証に失敗した場合、ブラウザにアラートを出し、メソッドを中止します。
- 18行目~:認証に成功した場合、HTMLのCSSクラスを切替え、リストの新規作成エリアを表示します。
認証情報を用いてFIREBASEのデータベースと通信する
最後に先ほど取得したtokenを用いて、FIREBASEのデータベースと通信します。
※以下のリスト新規作成メソッドは、ToDoリスト作成の記事で解説してますので、別記事をご参考ください。
// ★★todoの新規作成処理
async function createData() {
// バリデーション
if($newData.value.trim()==''){
alert('TODO登録データが入力されていません。')
return;
}
// フェッチ通信でFIREBASEへPOSTする
await fetch(
"https://ご自身のFIREBASEのURL/todo.json?auth="+token,//FIREBASEのURL+階層名+.json
{
method: "POST",
headers: {"Content-Type": "application/json",},
body: JSON.stringify({todo: $newData.value}), //入力値をJSONへ変換する
}
);
$newData.value=""; //インプットボックスを空欄
getData() //getDataメソッドでリストアイテムを最新化する
}
- 10行目:fetch通信のURLに、先ほどの認証でidTokenを格納したtoken情報を付与します。
動作確認
最後に動作確認を行います。ログイン認証が成功した後に、新規作成で「タスク4」を追加していきます。
先ほどはコンソールにエラーが表示されましたが、今度はエラー表示無く、リストへToDoが追加されています。
まとめ
今回の記事では、JavascriptやFIREBASEの初心者の方や、未経験からエンジニア転職を目指している方向けに、ユーザー認証機能の作成方法を解説しました。
自作のポートフォリオに機能を追加したいと考えている方は、ぜひ検討してみてください。