ldc-gen-game-web/app/Http/Controllers/Fo/Auth/VerificationController.php
2026-10-20 12:27:49 +02:00

138 lines
4.2 KiB
PHP

<?php
declare(strict_types=1);
namespace App\Http\Controllers\Fo\Auth;
use App\Http\Controllers\Controller;
use App\Models\Customer;
use Illuminate\Auth\Access\AuthorizationException;
use Illuminate\Auth\Events\Verified;
use Illuminate\Contracts\View\View;
use Illuminate\Foundation\Auth\VerifiesEmails;
use Illuminate\Http\Exceptions\HttpResponseException;
use Illuminate\Http\JsonResponse;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\DB;
use LDC\LDCCRM\Enums\ApiError;
use LDC\LDCCRM\Exceptions\ApiErrorException;
use LDC\LDCCRM\Exceptions\CrmException;
use LDC\LDCCRM\Exceptions\ValidationException;
class VerificationController extends Controller
{
use VerifiesEmails;
/**
* Create a new controller instance.
*/
public function __construct()
{
$this->middleware('auth:frontend')->except('verify');
$this->middleware('signed')->only('verify');
$this->middleware('throttle:6,1')->only('verify', 'resend');
}
/**
* Show the email verification notice.
*/
public function show(Request $request): RedirectResponse | View
{
/** @var view-string $view */
$view = 'theme::auth.verify';
return $request->user('frontend')->hasVerifiedEmail()
? redirect($this->redirectPath())
: view($view);
}
/**
* Mark the authenticated user's email address as verified.
*
* ! Overloaded trait
*
* @throws AuthorizationException If request is invalid.
*/
public function verify(Request $request): JsonResponse | RedirectResponse
{
/** @var Customer */
$user = Customer::findOrFail($request->route('id'));
throw_unless(hash_equals((string) $request->route('id'), (string) $user->getKey()), AuthorizationException::class);
throw_unless(hash_equals((string) $request->route('hash'), sha1($user->getEmailForVerification())), AuthorizationException::class);
if ($user->hasVerifiedEmail()) {
return $request->wantsJson()
? new JsonResponse([], 204)
: redirect($this->redirectPath());
}
DB::transaction(function () use ($user): void {
if ($user->markEmailAsVerified()) {
$this->setCrmCustomerAsVerified($user);
event(new Verified($user));
}
});
if ($response = $this->verified($request)) {
return $response;
}
return $request->wantsJson()
? new JsonResponse([], 204)
: redirect($this->redirectPath())->with('verified', true);
}
/**
* The user has been verified.
*
* @return mixed
*
* @phpcs:disable Generic.CodeAnalysis.UnusedFunctionParameter.FoundInExtendedClass
*/
protected function verified(Request $request)
{
// phpcs:enable
return redirect($this->redirectPath())->with('success', trans(
'front.messages.account_activated_can_play'
));
}
/**
* Get the post register / login redirect path.
*/
public function redirectPath(): string
{
return response()->redirectToRoute('fo.participate')->getTargetUrl();
}
/**
* Set Crm Customer active
*
* @throws HttpResponseException In case of failure.
*/
private function setCrmCustomerAsVerified(Customer $customer): void
{
try {
$customer->clearApiDataCache();
$crmCustomer = $customer->api_data;
$crmCustomer->activate();
$customer->clearApiDataCache();
} catch (ValidationException) {
redirect($this->redirectPath())->with('error', trans(
'front.messages.unexpected_error_try_later'
))->throwResponse();
} catch (CrmException | ApiErrorException $e) {
if ($e->getApiError()->equals(ApiError::customerAlreadyActive)) {
// * Ignore this and continue, as it may be activated via another CRM service.
return;
}
report($e);
redirect($this->redirectPath())->with('error', trans(
'front.messages.unexpected_error_try_later'
))->throwResponse();
}
}
}