krgm.so-manager-dev.com/resources/views/auth/otp.blade.php
OU.ZAIKOU 13d2ecfceb
All checks were successful
Deploy main / deploy (push) Successful in 25s
【ログイン】二重認証実装
2026-01-21 22:37:38 +09:00

172 lines
6.4 KiB
PHP
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

@extends('layouts.login')
@section('content')
<div class="login-box">
<div class="login-logo">
<a><b>So-Manager&nbsp;</b>{{ __('管理パネル') }}</a>
</div>
<!-- /.login-logo -->
<div class="card">
<div class="card-header">
<h5 class="mb-0">{{ __('セキュリティ認証') }}</h5>
</div>
<div class="card-body login-card-body">
<p class="login-box-msg mb-3">
{{ __('登録されたメールアドレス') }} <strong>{{ $maskedEmail }}</strong>
<br/>{{ __('に6桁の認証コードが送信されました。') }}
</p>
@if ($errors->any())
<div class="alert alert-danger alert-dismissible fade show" role="alert">
<strong>{{ __('エラー') }}</strong>
<ul class="mb-0">
@foreach ($errors->all() as $error)
<li>{{ $error }}</li>
@endforeach
</ul>
<button type="button" class="close" data-dismiss="alert" aria-label="Close">
<span aria-hidden="true">&times;</span>
</button>
</div>
@endif
@if (session('error'))
<div class="alert alert-danger alert-dismissible fade show" role="alert">
{{ session('error') }}
<button type="button" class="close" data-dismiss="alert" aria-label="Close">
<span aria-hidden="true">&times;</span>
</button>
</div>
@endif
@if (session('success'))
<div class="alert alert-success alert-dismissible fade show" role="alert">
{{ session('success') }}
<button type="button" class="close" data-dismiss="alert" aria-label="Close">
<span aria-hidden="true">&times;</span>
</button>
</div>
@endif
<form action="{{ route('otp.verify') }}" method="POST" novalidate>
@csrf
<div class="form-group mb-3">
<label for="code" class="form-label">
<strong>{{ __('認証コード6桁') }}</strong>
</label>
<div class="input-group mb-3">
<input
type="text"
id="code"
name="code"
class="form-control form-control-lg text-center"
placeholder="000000"
maxlength="6"
pattern="[0-9]{6}"
inputmode="numeric"
required
autofocus
value="{{ old('code') }}"
/>
<div class="input-group-append">
<span class="fa fa-key input-group-text"></span>
</div>
</div>
<small class="d-block text-muted">
{{ __('数字のみで6桁入力してください。有効期限は10分です。') }}
</small>
</div>
<div class="row mt40">
<div class="col-12 col-lg-8 offset-0 offset-lg-2">
<button type="submit" class="btn btn-lg btn-primary btn-block btn-flat">
{{ __('認証する') }}
</button>
</div>
</div>
</form>
<div class="text-center mt-3">
<form action="{{ route('otp.resend') }}" method="POST" class="d-inline">
@csrf
<button
type="submit"
class="btn btn-sm btn-outline-secondary"
id="resendBtn"
@if ($resendWaitSeconds > 0) disabled @endif
>
<span id="resendText">
@if ($resendWaitSeconds > 0)
{{ __('コード再送(') }}{{ $resendWaitSeconds }}{{ __('秒待機)') }}
@else
{{ __('コードを再送信する') }}
@endif
</span>
</button>
</form>
</div>
<div class="mt-3 text-center">
<a href="{{ route('logout') }}" class="text-muted small">
{{ __('ログアウト') }}
</a>
</div>
</div>
</div>
</div>
<script>
document.addEventListener('DOMContentLoaded', function() {
// 入力フィールドの自動フォーカス制御
const codeInput = document.getElementById('code');
const resendBtn = document.getElementById('resendBtn');
const resendText = document.getElementById('resendText');
// 数字のみ許可
codeInput.addEventListener('keypress', function(e) {
if (!/\d/.test(e.key)) {
e.preventDefault();
}
});
// 貼り付け時に数字のみを許可
codeInput.addEventListener('paste', function(e) {
e.preventDefault();
const pastedText = (e.clipboardData || window.clipboardData).getData('text');
const numbers = pastedText.replace(/\D/g, '').slice(0, 6);
codeInput.value = numbers;
});
// 再送ボタンのカウントダウン処理
let waitSeconds = {{ $resendWaitSeconds }};
if (waitSeconds > 0) {
const countdown = setInterval(function() {
waitSeconds--;
if (waitSeconds <= 0) {
clearInterval(countdown);
resendBtn.disabled = false;
resendText.textContent = '{{ __("コードを再送信する") }}';
} else {
resendText.textContent = '{{ __("コード再送(") }}' + waitSeconds + '{{ __("秒待機)") }}';
}
}, 1000);
}
});
</script>
<style>
#code {
letter-spacing: 0.5em;
font-size: 1.5rem;
font-weight: bold;
font-family: 'Courier New', monospace;
}
#code::placeholder {
letter-spacing: 0.5em;
}
</style>
@endsection