概要
バックエンド:SpringBoot RestApi
フロントエンド:Next.js TypeScript
でBtoC向けECショップのクローンサイトを作ってます。
今回はログイン機能を実装します。
下の記事の続きですね。
SpringBoot Rest-Apiメール認証付きユーザー登録機能の実装
前回はPostmanを使って挙動を確認しましたが、今回はフロントエンド側でページを作成 API処理を実行してユーザー登録できるようにします。
ユースケース
入力したメールアドレスが本当に所有者なのか確認するため、メールアドレス認証を行います。
1.ユーザーがEmailとPasswordを入力して登録ボタンを押す。
2.システムがデータベースにユーザーを”仮登録”の状態で登録して、認証するためにEmailを送信する。
3.ユーザーが認証メール中のリンクを押すと、登録完了される。
開発環境
OS:windows10
バックエンド側:
IDE:IntelliJ Community
spring-boot-starter-parent 2.75
java : 11
データベース
mysql:8.0.29
クライアントソフト: MySQL Workbench
フロントエンド:
IDE:VScode
├── @types/node@18.11.15
├── @types/react-dom@18.0.9
├── @types/react@18.0.26
├── axios@1.2.1
├── eslint-config-next@13.0.6
├── eslint@8.29.0
├── next-auth@4.18.7
├── next@13.0.6
├── react-bootstrap@2.7.0
├── react-dom@18.2.0
├── react@18.2.0
├── styled-components@5.3.6
├── styled-jsx@5.1.1
└── typescript@4.9.4
実装
作成したファイル一覧
バックエンド
以下リンク参照
SpringBoot Rest-Apiメール認証付きユーザー登録機能の実装
フロントエンド
主に作ったファイルはページ機能があるファイルです。
Next.jsの機能(routing DynamicRouting)を活用しています。
Reactは初回実行時するために、UseEffect使ったぐらいですね。
ファイル名 | 説明 |
---|---|
customerService.ts | api処理が入っている ライブラリはaxiosを利用 |
pages/regsiter.tsx | ユーザー情報を入力する時のページ |
pages/registerComplete.tsx | register.tsxでユーザー登録が成功した時に遷移するページ |
pages/verify/[code].tsx | メールのリンク先 URLに認証コードの値が入っている。ページを開くと初回実行時、ユーザーを有効化するApiを実行する next.jsのdynamicRouting機能を使ってます。 |
コード(長いので先に作成したファイル一覧をご覧ください)
customerService.ts
import axios from 'axios';
import { URLSearchParams } from 'url';
import { Customer } from '../types/customer';
import { response } from 'msw';
export const register= async (inputEmail:string,inputPassword:string) =>{
return await axios.post(`http://127.0.0.1:5000/api/auth/signup`,
{
'email':inputEmail,
'password':inputPassword
},
)
.then((response)=>{
return response;
})
.catch((error)=>{
return error;
})}
export const verify= async (verifyCode:string) =>{
return await axios.put(`http://127.0.0.1:5000/api/auth/verify`,
{
'verifyCode':verifyCode
},
{ headers : {
'Request-Method' : 'PUT',
'Content-Type': 'application/json',
'Access-Control-Allow-Origin': 'http://127.0.0.1:5000/*',
'Access-Control-Allow-Headers': 'accept, accept-language, content-language, content-type',
'Access-Control-Allow-Credentials': 'true'
}}
)
.then((response)=>{
return response;
})
.catch((error)=>{
return error;
})}
register.tsx
import { useState } from 'react';
import { Customer } from '../types/customer';
import * as customerService from "../service/customerService";
import Router from 'next/router';
// ユーザー登録ページ
// http://127.0.0.1:3000/register
export default function Register() {
let inputEmail :string;
let inputPassword :string;
// ボタンを押したときに実行する関数
const onRegisterClick = async (event: React.MouseEvent<HTMLButtonElement>) => {
// todo エラーハンドリングの実装
const response = await customerService.register(inputEmail,inputPassword);
Router.push('/registerComplete')
}
// Emailアドレスの入力値を変数に渡す
const onChangeEmailHandler = (e: React.FormEvent<HTMLInputElement>) => {
inputEmail=e.currentTarget.value;
}
// パスワードの入力値を変数に渡す
const onChangePasswordHandler = (e: React.FormEvent<HTMLInputElement>) => {
inputPassword=e.currentTarget.value;
}
return(
<div className="Layout">
<div>ユーザー登録画面</div>
入力したEメールに認証メールが送られます。
<div>Emailアドレス</div>
<input type="text" onChange={onChangeEmailHandler}></input>
<div>パスワード</div>
<input type="password" onChange={onChangePasswordHandler}></input>
<br/>
<br/>
<button onClick={onRegisterClick} >ユーザー登録</button>
<style jsx>{`
.Layout{
text-align: center;
}
`}</style>
</div>
)
}
registerComplete.tsx
// ユーザー登録が完了したときに表示するページ
export default function registerComplete(){
return(
<div>
仮登録が完了しました。
認証メールを送りましたので確認お願いします。
</div>
)
}
verify/[code].tsx
import { useRouter } from "next/router";
import {useEffect} from 'react';
import * as customerService from "../../service/customerService";
// 認証完了ページ
export default function Verify(){
// URLのペラメーターverify/〇〇の〇〇部分を変数に渡している
const {code} = useRouter().query;
// 初回実行時に実行する
useEffect(()=>{
verify();},[]);
// 認証コードを送信する関数
const verify = async()=> {
const response = await customerService.verify(code as string);
}
return (
<div>
認証が完了しました。
認証コード
<div>{code}</div>
</div>
)
}
実装後の検証
gifアニメは左側ブラウザでviewの確認、右側MySQL workbenchでDBを確認しています。
Emailとパスワードを入力して登録ボタンを押すまで
以下情報を入力
捨てメアドサイトで作った適当なアドレスです。
データベースに新しいユーザーが作成されていることを確認できます。
送られてきたメールのリンクをクリックして認証を完了する
メールのリンクを開くと、仮登録ユーザーのパラメーターが変化し認証が完了します。
enabled=true
virification_code=null
課題
例外処理が未実装なので、追加の必要あり
1.バリデーション
2.Eメールアドレスを送信できなかった場合
3.既に認証が完了してるのにリンクを開いた場合
4.ユーザー登録ボタン押したときの待ちが時間が気になった。(本当に動作してるのかわからない)