はじめに
前回に引き続きbootstrapのモーダル機能で新規登録・ログインフォームを作成方法をアウトプットします✍️
初心者ですので、もっといい方法があるよ!
等ございましたらご教示いただけますと幸いです!
開発環境
- ruby: 3.1.2
- Rails: 6.1.7.7
- Cloud9
- bootstrap: 4.6.2
前提条件
- bootstrap4.6.2 導入済み
- devise 導入済み
Javascriptでバリデーションを実装
新規登録やログインにエラーが発生した時、
deviseの使用上元の(モーダルでない)新規登録ページやログインページに飛んでしまいます
ログインを非同期で行うことも試みましたが挫折しました…
なので、今回はJavascriptで簡単なバリデーションをつけていきたいと思います
コード全体だけ見たいよ〜という方はこちらをクリックしてください↓
Javascriptコード全体
document.addEventListener('turbolinks:load', () => {
// 新規登録バリデーション
const registrationSubmitCheck = document.querySelector('#registration_submit');
if (registrationSubmitCheck) {
let nameError = false;
let emailError = false;
let passError = false;
let passConfirmError = false;
const registrationName = document.querySelector('#registration_name');
const registrationEmail = document.querySelector('#registration_email');
const registrationPass = document.querySelector('#registration_pass');
const registrationPassConfirm = document.querySelector('#registration_pass_confirm');
const registrationSubmit = document.querySelector('#registration_submit');
const inputs = [registrationName, registrationEmail, registrationPass, registrationPassConfirm];
inputs.forEach(input => {
input.addEventListener('input', () => {
updateSubmit();
});
});
// ユーザー名のinputイベントを監視
registrationName.addEventListener('input', function() {
let name = this.value;
if (name.length < 1) {
nameError = true;
document.querySelector('#nameError').textContent = 'ユーザー名を入力してください。';
document.querySelector('#nameError').style.display = 'block';
updateSubmit();
} else {
fetch(`/users/check_name?name=${name}`)
.then(response => response.json())
.then(data => {
if (data.status === false) {
nameError = true;
document.querySelector('#nameError').textContent = 'このユーザー名は既に登録されています。';
document.querySelector('#nameError').style.display = 'block';
} else {
nameError = false;
document.querySelector('#nameError').style.display = 'none';
}
updateSubmit();
})
.catch(error => {
console.log("AJAXリクエスト失敗:", error);
});
}
});
registrationEmail.addEventListener('input', function() {
let email = this.value;
let emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
if (!emailRegex.test(email)) {
emailError = true;
document.querySelector('#emailError').textContent = 'メールアドレスの形式が正しくありません。';
document.querySelector('#emailError').style.display = 'block';
updateSubmit();
} else {
fetch(`/users/check_email?email=${email}`)
.then(response => response.json())
.then(data => {
if (data.status === false) {
emailError = true;
document.querySelector('#emailError').textContent = 'このメールアドレスは既に登録されています。';
document.querySelector('#emailError').style.display = 'block';
} else {
emailError = false;
document.querySelector('#emailError').style.display = 'none';
}
updateSubmit();
})
.catch(error => {
console.log("AJAXリクエスト失敗:", error);
});
}
});
// パスワードフィールドのinputイベントを監視
registrationPass.addEventListener('input', function() {
if (this.value.length < 6) {
passError = true;
updatePasswordError();
document.querySelector('#passError').style.display = 'block';
} else {
passError = false;
document.querySelector('#passError').style.display = 'none';
}
updateSubmit();
});
// パスワード最低文字数カウント
function updatePasswordError() {
let remaining = 6 - registrationPass.value.length;
document.querySelector('#remainingChars').textContent = remaining;
}
// パスワード確認フィールドのinputイベントを監視
registrationPassConfirm.addEventListener('input', function() {
if (this.value !== registrationPass.value) {
passConfirmError = true;
document.querySelector('#passConfirmError').style.display = 'block';
} else {
passConfirmError = false;
document.querySelector('#passConfirmError').style.display = 'none';
}
updateSubmit();
});
function updateSubmit() {
if (registrationName.value.trim() === '' ||
registrationEmail.value.trim() === '' ||
registrationPass.value.trim() === '' ||
registrationPassConfirm.value.trim() === '' ||
nameError || emailError || passError || passConfirmError) {
registrationSubmit.classList.add('disabled');
registrationSubmit.setAttribute('disabled', true);
} else {
registrationSubmit.classList.remove('disabled');
registrationSubmit.removeAttribute('disabled');
}
}
}
// ログインバリデーション
const loginSubmitCheck = document.querySelector('#login_submit');
if (loginSubmitCheck) {
let loginEmailError = false;
let loginPassError = false;
let loginError = false;
document.querySelectorAll('#login_email, #login_pass').forEach(element => {
element.addEventListener('input', function() {
if (document.querySelector('#login_email').value.trim() === '' || document.querySelector('#login_pass').value.trim() === '') {
document.querySelector('#login_submit').classList.add('disabled');
document.querySelector('#login_submit').setAttribute('disabled', true);
} else if (loginEmailError || loginPassError || loginError) {
document.querySelector('#login_submit').classList.add('disabled');
document.querySelector('#login_submit').setAttribute('disabled', true);
} else {
document.querySelector('#login_submit').classList.remove('disabled');
document.querySelector('#login_submit').removeAttribute('disabled');
}
});
});
// メールアドレスのinputイベントを監視
document.querySelector('#login_email').addEventListener('input', function() {
let email = this.value;
let emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
if (!emailRegex.test(email)) {
document.querySelector('#loginEmailError').textContent = 'メールアドレスの形式が正しくありません。';
document.querySelector('#loginEmailError').style.display = 'block';
loginEmailError = true;
} else {
document.querySelector('#loginEmailError').style.display = 'none';
loginEmailError = false;
}
updateLoginSubmit();
});
// パスワードフィールドのinputイベントを監視
document.querySelector('#login_pass').addEventListener('input', function() {
if (this.value.length < 6) {
updateLoginPasswordError();
document.querySelector('#loginPassError').style.display = 'block';
loginPassError = true;
} else {
document.querySelector('#loginPassError').style.display = 'none';
loginPassError = false;
}
updateLoginSubmit();
});
// パスワード最低文字数カウント
function updateLoginPasswordError() {
let remaining = 6 - document.querySelector('#login_pass').value.length;
document.querySelector('#loginRemainingChars').textContent = remaining;
}
function updateLoginSubmit() {
if (document.querySelector('#login_email').value.trim() === '' || document.querySelector('#login_pass').value.trim() === '' || loginEmailError || loginPassError) {
document.querySelector('#login_submit').classList.add('disabled');
document.querySelector('#login_submit').setAttribute('disabled', true);
} else {
document.querySelector('#login_submit').classList.remove('disabled');
document.querySelector('#login_submit').removeAttribute('disabled');
}
}
document.addEventListener("ajax:success", function(e) {
let data = e.detail[0];
if (data.status === true) {
location.href = "/";
} else if (data.status === false) {
document.querySelector('#loginError').textContent = 'メールアドレスまたはパスワードが間違っています。';
document.querySelector('#loginError').style.display = 'block';
} else if (data.status === "inactive") {
document.querySelector('#loginError').textContent = '退会済みです。別のメールアドレスをお使いください。';
document.querySelector('#loginError').style.display = 'block';
}
});
document.addEventListener("ajax:error", function(e) {
document.querySelector('#loginError').textContent = '通信エラーが発生しました。';
document.querySelector('#loginError').style.display = 'block';
});
}
});
新規登録バリデーション
新規登録バリデーション Javascriptコード全体
// 新規登録バリデーション
const registrationSubmitCheck = document.querySelector('#registration_submit');
if (registrationSubmitCheck) {
let nameError = false;
let emailError = false;
let passError = false;
let passConfirmError = false;
const registrationName = document.querySelector('#registration_name');
const registrationEmail = document.querySelector('#registration_email');
const registrationPass = document.querySelector('#registration_pass');
const registrationPassConfirm = document.querySelector('#registration_pass_confirm');
const registrationSubmit = document.querySelector('#registration_submit');
const inputs = [registrationName, registrationEmail, registrationPass, registrationPassConfirm];
inputs.forEach(input => {
input.addEventListener('input', () => {
updateSubmit();
});
});
// ユーザー名のinputイベントを監視
registrationName.addEventListener('input', function() {
let name = this.value;
if (name.length < 1) {
nameError = true;
document.querySelector('#nameError').textContent = 'ユーザー名を入力してください。';
document.querySelector('#nameError').style.display = 'block';
updateSubmit();
} else {
fetch(`/users/check_name?name=${name}`)
.then(response => response.json())
.then(data => {
if (data.status === false) {
nameError = true;
document.querySelector('#nameError').textContent = 'このユーザー名は既に登録されています。';
document.querySelector('#nameError').style.display = 'block';
} else {
nameError = false;
document.querySelector('#nameError').style.display = 'none';
}
updateSubmit();
})
.catch(error => {
console.log("AJAXリクエスト失敗:", error);
});
}
});
registrationEmail.addEventListener('input', function() {
let email = this.value;
let emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
if (!emailRegex.test(email)) {
emailError = true;
document.querySelector('#emailError').textContent = 'メールアドレスの形式が正しくありません。';
document.querySelector('#emailError').style.display = 'block';
updateSubmit();
} else {
fetch(`/users/check_email?email=${email}`)
.then(response => response.json())
.then(data => {
if (data.status === false) {
emailError = true;
document.querySelector('#emailError').textContent = 'このメールアドレスは既に登録されています。';
document.querySelector('#emailError').style.display = 'block';
} else {
emailError = false;
document.querySelector('#emailError').style.display = 'none';
}
updateSubmit();
})
.catch(error => {
console.log("AJAXリクエスト失敗:", error);
});
}
});
// パスワードフィールドのinputイベントを監視
registrationPass.addEventListener('input', function() {
if (this.value.length < 6) {
passError = true;
updatePasswordError();
document.querySelector('#passError').style.display = 'block';
} else {
passError = false;
document.querySelector('#passError').style.display = 'none';
}
updateSubmit();
});
// パスワード最低文字数カウント
function updatePasswordError() {
let remaining = 6 - registrationPass.value.length;
document.querySelector('#remainingChars').textContent = remaining;
}
// パスワード確認フィールドのinputイベントを監視
registrationPassConfirm.addEventListener('input', function() {
if (this.value !== registrationPass.value) {
passConfirmError = true;
document.querySelector('#passConfirmError').style.display = 'block';
} else {
passConfirmError = false;
document.querySelector('#passConfirmError').style.display = 'none';
}
updateSubmit();
});
function updateSubmit() {
if (registrationName.value.trim() === '' ||
registrationEmail.value.trim() === '' ||
registrationPass.value.trim() === '' ||
registrationPassConfirm.value.trim() === '' ||
nameError || emailError || passError || passConfirmError) {
registrationSubmit.classList.add('disabled');
registrationSubmit.setAttribute('disabled', true);
} else {
registrationSubmit.classList.remove('disabled');
registrationSubmit.removeAttribute('disabled');
}
}
}
ブロックに分けて記載していきます
登録ボタンについて
まず前提として、新規登録フォームのsubmitボタンはデフォルトで表示された時クリックできないように実装しています
<%= f.submit "登録", disabled: true, class: "disabled", id: "registration_submit" %>
.disabled {
cursor: not-allowed;
}
HTMLの機能でdisabled: true
と記述するだけです!
自動でボタンの色がグレーっぽくなります
class: "disabled"
でcssの記述によりホバーした時にカーソルがバツになります
const registrationSubmitCheck = document.querySelector('#registration_submit');
if (registrationSubmitCheck) {
let nameError = false;
let emailError = false;
let passError = false;
let passConfirmError = false;
const registrationName = document.querySelector('#registration_name');
const registrationEmail = document.querySelector('#registration_email');
const registrationPass = document.querySelector('#registration_pass');
const registrationPassConfirm = document.querySelector('#registration_pass_confirm');
const registrationSubmit = document.querySelector('#registration_submit');
const inputs = [registrationName, registrationEmail, registrationPass, registrationPassConfirm];
inputs.forEach(input => {
input.addEventListener('input', () => {
updateSubmit();
});
});
:
function updateSubmit() {
if (registrationName.value.trim() === '' ||
registrationEmail.value.trim() === '' ||
registrationPass.value.trim() === '' ||
registrationPassConfirm.value.trim() === '' ||
nameError || emailError || passError || passConfirmError) {
registrationSubmit.classList.add('disabled');
registrationSubmit.setAttribute('disabled', true);
} else {
registrationSubmit.classList.remove('disabled');
registrationSubmit.removeAttribute('disabled');
}
}
let nameError = false;
などは、エラー状態かを表します
false
だとエラーでない状態、true
だとエラー状態を意味します
初期値はエラーでないfalse
です
const registrationName = document.querySelector('#registration_name');
const registrationEmail = document.querySelector('#registration_email');
const registrationPass = document.querySelector('#registration_pass');
const registrationPassConfirm = document.querySelector('#registration_pass_confirm');
const registrationSubmit = document.querySelector('#registration_submit');
const inputs = [registrationName, registrationEmail, registrationPass, registrationPassConfirm];
inputs.forEach(input => {
input.addEventListener('input', () => {
updateSubmit();
});
});
このコードは4つの入力フィールドのinputイベント(入力イベント)を監視し、
フィールドに何かしらの入力があった場合はupdateSubmit
関数が呼び出されます
function updateSubmit() {
if (registrationName.value.trim() === '' ||
registrationEmail.value.trim() === '' ||
registrationPass.value.trim() === '' ||
registrationPassConfirm.value.trim() === '' ||
nameError || emailError || passError || passConfirmError) {
registrationSubmit.classList.add('disabled');
registrationSubmit.setAttribute('disabled', true);
} else {
registrationSubmit.classList.remove('disabled');
registrationSubmit.removeAttribute('disabled');
}
}
updateSubmit
関数では以下のことが行われています
・.value.trim() === ''
で4つのフィールドが空白でないか確認します
(.trim()
は、前後の空白を取り除く)
・エラーフラグを確認します
(nameError
など4つ全てがエラー状態でないことを確認)
・エラーが一つでもある場合登録ボタンはクリックできないまま(一つでもtrueがある場合)
・エラーが一つもない場合登録ボタンをクリックできるようにする(全てfalseだった場合)
(classのdisabledを削除して、disabled属性をfalseに変える↓)
- <%= f.submit "登録", disabled: true, class: "disabled", id: "registration_submit" %>
+ <%= f.submit "登録", disabled: false, class: "", id: "registration_submit" %>
また、Javascriptにおいて==
と===
の違いは以下の記事がわかりやすかったです
ユーザー名のバリデーション(ajax使うよ)
// ユーザー名のinputイベントを監視
registrationName.addEventListener('input', function() {
let name = this.value;
if (name.length < 1) {
nameError = true;
document.querySelector('#nameError').textContent = 'ユーザー名を入力してください。';
document.querySelector('#nameError').style.display = 'block';
updateSubmit();
} else {
fetch(`/users/check_name?name=${name}`)
.then(response => response.json())
.then(data => {
if (data.status === false) {
nameError = true;
document.querySelector('#nameError').textContent = 'このユーザー名は既に登録されています。';
document.querySelector('#nameError').style.display = 'block';
} else {
nameError = false;
document.querySelector('#nameError').style.display = 'none';
}
updateSubmit();
})
.catch(error => {
console.log("AJAXリクエスト失敗:", error);
});
}
});
registrationName.addEventListener('input', function() {
let name = this.value;
if (name.length < 1) {
nameError = true;
document.querySelector('#nameError').textContent = 'ユーザー名を入力してください。';
document.querySelector('#nameError').style.display = 'block';
updateSubmit();
ユーザー名の入力フィールドのinputイベント(入力イベント)を監視し、
何かしら入力された後に、deleteなどで文字数が1未満になった時、
「ユーザー名を入力してください。」というエラー文がnameError
のidが付与されている箇所に表示されます↓
<%= f.text_field :name, id: "registration_name"%>
<div id="nameError""></div>
次に、条件分岐で1文字以上入力されている時の処理です
} else {
fetch(`/users/check_name?name=${name}`)
.then(response => response.json())
.then(data => {
ajaxでurlから欲しいデータを取得します
そのためにはルーティングとuserコントローラにアクションを記述する必要があります
今回はpublicとadminにルーティングを分けていますのでご留意ください
Rails.application.routes.draw do
devise_for :users, controllers: {
registrations: 'public/registrations',
sessions: 'public/sessions',
}
:
scope module: :public do
:
get 'users/check_name' => 'users#check_name'
end
:
end
class Public::UsersController < ApplicationController
before_action :authenticate_user!, except: [:check_name]
:
def check_name
name = params[:name]
user = User.find_by(name: name)
render json: user.nil? ? {status: true}.to_json : {status: false}.to_json
end
:
end
フォームに入力されたユーザー名をfine_by
で検索
ユーザーがnilの場合は{status: true}
をjson形式返し、入力されたユーザー名と同一のユーザー名がデータベースに保存されている場合は、{status: false}
をjson形式で返します
if (data.status === false) {
nameError = true;
document.querySelector('#nameError').textContent = 'このユーザー名は既に登録されています。';
document.querySelector('#nameError').style.display = 'block';
} else {
nameError = false;
document.querySelector('#nameError').style.display = 'none';
}
updateSubmit();
})
.catch(error => {
console.log("AJAXリクエスト失敗:", error);
});
もしajaxで取得したデータが {status: false}
の場合
・nameError
をtrue
にします(エラー状態を意味します)
・「このユーザー名は既に登録されています。」というエラー文がnameError
のidが付与されている箇所に表示されます↓
<%= f.text_field :name, id: "registration_name"%>
<div id="nameError""></div>
もしajaxで取得したデータが {status: true}
の場合
・nameError
のidが付与されている箇所が非表示になります
もしajaxで取得したデータが {status: error}
の場合
・AJAXリクエスト失敗とコンソールに表示されます
メールアドレスのバリデーション
最初の部分以外はユーザー名と同じなので省略します
registrationEmail.addEventListener('input', function() {
let email = this.value;
let emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
if (!emailRegex.test(email)) {
emailError = true;
document.querySelector('#emailError').textContent = 'メールアドレスの形式が正しくありません。';
document.querySelector('#emailError').style.display = 'block';
updateSubmit();
ここで正規表現を利用して、「⚪︎⚪︎@⚪︎⚪︎.⚪︎⚪︎」の形式であることをチェックしています
パスワードのバリデーション
// パスワードフィールドのinputイベントを監視
registrationPass.addEventListener('input', function() {
if (this.value.length < 6) {
passError = true;
updatePasswordError();
document.querySelector('#passError').style.display = 'block';
} else {
passError = false;
document.querySelector('#passError').style.display = 'none';
}
updateSubmit();
});
// パスワード最低文字数カウント
function updatePasswordError() {
let remaining = 6 - registrationPass.value.length;
document.querySelector('#remainingChars').textContent = remaining;
}
入力されたパスワードが6文字以上かチェックしています
6文字未満の場合passError
のidが付与されているエラー文が表示され、
6から入力された文字数を引いた数をremainingChars
のidが付与されている箇所に挿入します↓
<%= f.password_field :password, autocomplete: "new-password", id: "registration_pass" %>
<div id="passError">パスワードを入力してください(あと<span id="remainingChars"></span>文字)。</div>
パスワード確認のバリデーション
registrationPassConfirm.addEventListener('input', function() {
if (this.value !== registrationPass.value) {
passConfirmError = true;
document.querySelector('#passConfirmError').style.display = 'block';
} else {
passConfirmError = false;
document.querySelector('#passConfirmError').style.display = 'none';
}
updateSubmit();
});
入力されたパスワード確認をパスワードと一致するかチェックし、一致しなければ
passConfirmError
のidが付与されているエラー文が表示されます↓
<%= f.password_field :password_confirmation, autocomplete: "new-password", id: "registration_pass_confirm" %>
<div id="passConfirmError">パスワードが一致していません。</div>
ログインバリデーション
ログインバリデーション Javascriptコード全体
// ログインバリデーション
const loginSubmitCheck = document.querySelector('#login_submit');
if (loginSubmitCheck) {
let loginEmailError = false;
let loginPassError = false;
let loginError = false;
document.querySelectorAll('#login_email, #login_pass').forEach(element => {
element.addEventListener('input', function() {
if (document.querySelector('#login_email').value.trim() === '' || document.querySelector('#login_pass').value.trim() === '') {
document.querySelector('#login_submit').classList.add('disabled');
document.querySelector('#login_submit').setAttribute('disabled', true);
} else if (loginEmailError || loginPassError || loginError) {
document.querySelector('#login_submit').classList.add('disabled');
document.querySelector('#login_submit').setAttribute('disabled', true);
} else {
document.querySelector('#login_submit').classList.remove('disabled');
document.querySelector('#login_submit').removeAttribute('disabled');
}
});
});
// メールアドレスのinputイベントを監視
document.querySelector('#login_email').addEventListener('input', function() {
let email = this.value;
let emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
if (!emailRegex.test(email)) {
document.querySelector('#loginEmailError').textContent = 'メールアドレスの形式が正しくありません。';
document.querySelector('#loginEmailError').style.display = 'block';
loginEmailError = true;
} else {
document.querySelector('#loginEmailError').style.display = 'none';
loginEmailError = false;
}
updateLoginSubmit();
});
// パスワードフィールドのinputイベントを監視
document.querySelector('#login_pass').addEventListener('input', function() {
if (this.value.length < 6) {
updateLoginPasswordError();
document.querySelector('#loginPassError').style.display = 'block';
loginPassError = true;
} else {
document.querySelector('#loginPassError').style.display = 'none';
loginPassError = false;
}
updateLoginSubmit();
});
// パスワード最低文字数カウント
function updateLoginPasswordError() {
let remaining = 6 - document.querySelector('#login_pass').value.length;
document.querySelector('#loginRemainingChars').textContent = remaining;
}
function updateLoginSubmit() {
if (document.querySelector('#login_email').value.trim() === '' || document.querySelector('#login_pass').value.trim() === '' || loginEmailError || loginPassError) {
document.querySelector('#login_submit').classList.add('disabled');
document.querySelector('#login_submit').setAttribute('disabled', true);
} else {
document.querySelector('#login_submit').classList.remove('disabled');
document.querySelector('#login_submit').removeAttribute('disabled');
}
}
document.addEventListener("ajax:success", function(e){
let data = e.detail[0];
if (data.status === true) {
location.href = "/";
} else {
document.querySelector('#loginError').textContent = 'メールアドレスまたはパスワードが間違っています。';
document.querySelector('#loginError').style.display = 'block';
}
});
document.addEventListener("ajax:error", function(e) {
document.querySelector('#loginError').textContent = '通信エラーが発生しました。';
document.querySelector('#loginError').style.display = 'block';
});
}
ユーザー名とメールアドレスについては新規登録と同じなので省略します
ログインフォームURLについて
まず前提として、ログインフォームのURLはajaxのデータ送信に使用します
理由はログインボタンをクリックして入力情報が誤っていたときにモーダル上でエラー文を表示できないためです(モーダルでない元のログインページにリダイレクトしてしまいます)
<%= form_with model: resource, url: users_check_user_path, local: false, class: 'sessions' do |f| %>
Rails.application.routes.draw do
devise_for :users, controllers: {
registrations: 'public/registrations',
sessions: 'public/sessions',
}
:
scope module: :public do
:
post 'users/check_user' => 'users#check_user'
end
:
end
今回ルーティングがgetでなくpostなのはパスワードがURLに表示されてしまうことを防ぐためです
class Public::UsersController < ApplicationController
before_action :authenticate_user!, except: [:check_user]
:
def check_user
user = User.find_by(email: params[:user][:email])
if !user.nil? && user.valid_password?(params[:user][:password])
if user.is_active?
sign_in user
flash[:notice] = "ログインしました。"
render json: {status: true}.to_json
else
render json: {status: "inactive"}.to_json
end
else
render json: {status: false}.to_json
end
end
:
end
ajaxによって送信されたemailを他のユーザーがすでに登録しているかfine_byで確認します
一致していた場合はsign_in user
でログインし、{status: true}
を返します
一致しなかった場合は、{status: false}
を返します
ログインエラー
document.addEventListener("ajax:success", function(e) {
let data = e.detail[0];
if (data.status === true) {
location.href = "/";
} else if (data.status === false) {
document.querySelector('#loginError').textContent = 'メールアドレスまたはパスワードが間違っています。';
document.querySelector('#loginError').style.display = 'block';
} else if (data.status === "inactive") {
document.querySelector('#loginError').textContent = '退会済みです。別のメールアドレスをお使いください。';
document.querySelector('#loginError').style.display = 'block';
}
});
{status: true}
がtrueであればトップページ(URLが/)に飛び、
{status: false}
であればloginError'
のidが付与されている箇所に「メールアドレスまたはパスワードが間違っています。」というエラー文が表示されます↓
<div id="loginError"></div>
さいごに
最初はjQueryで書いてましたが、最近はjQueryを使わず素のJavascriptで書くことが多くなってきたらしいです!ということで素のJavascriptに書き換えました(ChatGPTでですが💦)
修正点等ございましたらご教示お願いいたします!