require 2fa if enabled
CI/CD / test_and_check_app (push) Failing after 47s
CI/CD / Publish immutable image (push) Skipped

This commit is contained in:
2026-10-08 11:29:28 +02:00
parent f2b12c36af
commit b6e0ec539c
6 changed files with 40 additions and 15 deletions
+2 -3
View File
@@ -17,7 +17,7 @@ class CreateNewUser implements CreatesNewUsers
use PasswordValidationRules, ProfileValidationRules;
public function __construct(
private AcceptTeamInvite $acceptTeamInvite,
private readonly AcceptTeamInvite $acceptTeamInvite,
) {}
/**
@@ -59,8 +59,7 @@ class CreateNewUser implements CreatesNewUsers
]);
if ($invite !== null) {
$invite->team->members()->attach($user);
$invite->delete();
($this->acceptTeamInvite)($invite, $user);
}
return $user;
+9 -3
View File
@@ -5,15 +5,21 @@ namespace App\Actions\Teams;
use App\Models\TeamInvite;
use App\Models\User;
use Illuminate\Support\Facades\DB;
use Illuminate\Validation\ValidationException;
readonly class AcceptTeamInvite
{
public function __invoke(TeamInvite $invite): void
public function __invoke(TeamInvite $invite, User $newUser): void
{
abort_unless(auth()->user()->email === $invite->invited_email, 403);
abort_unless($newUser->email === $invite->invited_email, 403);
$team = $invite->team;
$newUser = User::whereEmail($invite->invited_email)->firstOrFail();
if ($invite->team->require_2fa && ! $newUser->hasEnabledTwoFactorAuthentication()) {
throw ValidationException::withMessages([
'require_2fa' => 'Du musst 2FA einrichten, damit du dem Team beitreten kannst',
]);
}
try {
DB::transaction(function () use ($team, $newUser, $invite) {
+21 -3
View File
@@ -15,6 +15,7 @@ use Illuminate\Http\Request;
use Illuminate\Support\Arr;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Str;
use Illuminate\Validation\ValidationException;
use Inertia\Inertia;
use Inertia\Response;
@@ -50,10 +51,18 @@ class TeamController extends Controller
*/
public function store(StoreTeamRequest $request): RedirectResponse
{
$validated = $request->validated();
$user = $request->user();
if (Arr::get($validated, 'require_2fa', false) && ! $user->hasEnabledTwoFactorAuthentication()) {
throw ValidationException::withMessages([
'require_2fa' => 'Du musst 2FA einrichten, damit du 2FA aktivieren kannst!',
]);
}
try {
DB::transaction(function () use ($request): void {
$team = Team::create($request->validated());
$team->members()->attach($request->user(), ['role' => TeamMemberRole::Owner]);
DB::transaction(function () use ($validated, $user): void {
$team = Team::create($validated);
$team->members()->attach($user, ['role' => TeamMemberRole::Owner]);
});
} catch (\Exception $exception) {
report($exception);
@@ -87,6 +96,15 @@ class TeamController extends Controller
*/
public function update(UpdateTeamRequest $request, Team $team): RedirectResponse
{
$validated = $request->validated();
$user = $request->user();
if (Arr::get($validated, 'require_2fa', false) && ! $user->hasEnabledTwoFactorAuthentication()) {
throw ValidationException::withMessages([
'require_2fa' => 'Du musst 2FA einrichten, damit du 2FA aktivieren kannst!',
]);
}
try {
$team->update($request->validated());
} catch (\Exception $exception) {
@@ -17,7 +17,7 @@ class TeamInviteAcceptController extends Controller
$invite = TeamInvite::findByPlainToken($inviteToken)->first();
if ($invite) {
$accept($invite);
$accept($invite, $request->user());
return to_route('teams.index');
}
@@ -32,7 +32,7 @@ class TeamInviteAcceptController extends Controller
{
$request->validated();
$accept($request->teamInvite());
$accept($request->teamInvite(), $request->user());
return to_route('teams.index');
}
+1
View File
@@ -102,6 +102,7 @@ defineOptions({
/>
<InputError :message="errors.invite_token" />
</div>
<InputError :message="errors.require_2fa" />
<Button
:disabled="processing"
+5 -4
View File
@@ -1,10 +1,10 @@
<script lang="ts" setup>
import teamRoutes from '@/routes/teams';
import { Form, Head, useForm } from '@inertiajs/vue3';
import { Card, CardContent } from '@/components/ui/card';
import { Input } from '@/components/ui/input';
import {Form, Head, useForm} from '@inertiajs/vue3';
import {Card, CardContent} from '@/components/ui/card';
import {Input} from '@/components/ui/input';
import InputError from '@/components/InputError.vue';
import { Button } from '@/components/ui/button';
import {Button} from '@/components/ui/button';
defineOptions({
layout: {
@@ -49,6 +49,7 @@ const submit = () => form.post(teamRoutes.invite.store().url);
/>
<InputError :message="form.errors.inviteToken" />
</div>
<InputError :message="(form.errors as any).require_2fa" />
<div class="flex w-full justify-end">
<Button :disabled="form.processing" type="submit"
>Team Beitreten</Button