Skip to content

確認コード画面に再送信と登録やり直しの導線を追加する - #13

Merged
uswebk merged 2 commits into
mainfrom
feature/verify-otp-resend
Jul 14, 2026
Merged

確認コード画面に再送信と登録やり直しの導線を追加する#13
uswebk merged 2 commits into
mainfrom
feature/verify-otp-resend

Conversation

@uswebk

@uswebk uswebk commented Jul 13, 2026

Copy link
Copy Markdown
Owner

背景

サインアップ後に /verify-otp へ飛ばされると、そこから抜ける手段が「正しい確認コードを入力すること」しかなかった。

  • OTPはサインアップ時に1回だけ送信される(apps/api/src/routes/auth.ts
  • Better Auth のデフォルトは有効期限5分・試行3回
  • _app.tsx / select-site.tsx / login.tsx のガードが emailVerified === false なら無条件に /verify-otp へ戻す

そのため、メールの見逃し・期限切れ・メールアドレスの打ち間違いのいずれでも、ログインし直しても永久に確認画面に閉じ込められていた。

変更内容

  • 確認コードの再送信(60秒クールダウン)。サインアップ直後に1通送られているため初期状態もクールダウンから開始する。API追加は不要で、Better Auth の emailOtp.sendVerificationOtp() を呼ぶだけ
  • エラーの区別OTP_EXPIRED / TOO_MANY_ATTEMPTS は専用メッセージを出し、そのコードはもう成功しえないためクールダウンを解除して即再送信できるようにした(それ以外は従来どおり「コードが正しくありません」)
  • 送信先メールアドレスを強調表示し、誤りにその場で気づけるようにした
  • 「別のメールアドレスで登録し直す」導線。未認証アカウントはメールアドレスを変更できないため、セッションを破棄してサインアップに戻す
  • emailOTPexpiresIn: 600(10分。自前のメール変更OTPと同じTTL)と allowedAttempts: 3 を明示
  • これまで仕様が空白だった有効期限・再送信・試行回数を docs/domain/auth.md に追記

動作確認

ローカルAPI + mailpit に対して実行し、以下を確認済み。

  1. 再送信すると新しいコードが届く
  2. 誤ったコード4回目で TOO_MANY_ATTEMPTS が返る
  3. その状態から再送信した新コードで認証成功 → emailVerified: true になりガードが解ける

biome check / tsc --noEmit は変更ファイルでクリーン。

🤖 Generated with Claude Code

uswebk and others added 2 commits July 13, 2026 22:48
サインアップ後の /verify-otp から抜ける手段が正しいOTPの入力しかなく、
コードは1回しか送られないためメールの見逃し・期限切れ・メールアドレスの
打ち間違いで閉じ込められていた。

- 確認コードの再送信(60秒クールダウン)を追加
- 期限切れ・試行回数超過を個別のメッセージで案内し、その場合は
  クールダウンを解除して即再送信できるようにする
- 送信先メールアドレスを強調表示し、誤りに気づけるようにする
- 「別のメールアドレスで登録し直す」導線を追加(未認証アカウントは
  メールアドレスを変更できないため、サインアップからやり直す)
- OTPの有効期限を10分・試行回数を3回として明示する

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
再送信のクールダウンがフロントのstateのみで、リロードすれば無制限に
メールを送信できる状態だった。Better Authのレート制限で送信APIを
60秒に1回に制限し、フロントはX-Retry-Afterに従うようにする。
クールダウンは締切時刻をsessionStorageに保存し、リロードをまたいで復元する。

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
@uswebk
uswebk merged commit 0972eda into main Jul 14, 2026
3 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant