seed(RolesAndPermissionsSeeder::class); }); test('requesting access for an unknown email creates nothing and sends no mail', function () { /** @var TestCase $this */ Mail::fake(); $sent = app(ContactAccessService::class)->requestAccess('nobody@example.test'); expect($sent)->toBeFalse(); expect(User::query()->where('email', 'nobody@example.test')->exists())->toBeFalse(); Mail::assertNothingSent(); }); test('requesting access for a known contact lazily creates a scoped account and sends a link', function () { /** @var TestCase $this */ Mail::fake(); $company = Company::factory()->presseecho()->create(); Contact::factory()->for($company)->create([ 'email' => 'paula@example.test', 'first_name' => 'Paula', 'last_name' => 'Presse', 'portal' => $company->portal->value, ]); // Gross-/Kleinschreibung egal. $sent = app(ContactAccessService::class)->requestAccess('Paula@Example.test'); expect($sent)->toBeTrue(); $user = User::query()->where('email', 'paula@example.test')->firstOrFail(); expect($user->name)->toBe('Paula Presse'); expect($user->is_active)->toBeTrue(); expect($user->hasVerifiedEmail())->toBeTrue(); expect($user->hasRole('customer'))->toBeTrue(); expect($user->canAccessAdmin())->toBeFalse(); expect($user->canAccessCustomer())->toBeTrue(); expect($user->accessibleCompanyIds())->toContain($company->id); Mail::assertSent(MagicLoginLink::class, fn (MagicLoginLink $mail) => $mail->user->is($user)); }); test('requesting access reuses an existing user without creating a duplicate', function () { /** @var TestCase $this */ Mail::fake(); $company = Company::factory()->presseecho()->create(); Contact::factory()->for($company)->create([ 'email' => 'existing@example.test', 'portal' => $company->portal->value, ]); $existing = User::factory()->create(['email' => 'existing@example.test', 'is_active' => true]); $existing->assignRole('customer'); app(ContactAccessService::class)->requestAccess('existing@example.test'); expect(User::query()->where('email', 'existing@example.test')->count())->toBe(1); expect($existing->fresh()->accessibleCompanyIds())->toContain($company->id); Mail::assertSent(MagicLoginLink::class); }); test('the contact access form responds neutrally and triggers the service', function () { /** @var TestCase $this */ Mail::fake(); $company = Company::factory()->presseecho()->create(); Contact::factory()->for($company)->create([ 'email' => 'form@example.test', 'portal' => $company->portal->value, ]); Volt::test('auth.contact-access') ->set('email', 'form@example.test') ->call('requestAccess') ->assertHasNoErrors() ->assertSet('email', ''); Mail::assertSent(MagicLoginLink::class); expect(User::query()->where('email', 'form@example.test')->exists())->toBeTrue(); }); test('the honeypot blocks bots without creating an account', function () { /** @var TestCase $this */ Mail::fake(); $company = Company::factory()->presseecho()->create(); Contact::factory()->for($company)->create([ 'email' => 'bot-target@example.test', 'portal' => $company->portal->value, ]); Volt::test('auth.contact-access') ->set('email', 'bot-target@example.test') ->set('website', 'http://spam.example') ->call('requestAccess') ->assertHasNoErrors(); Mail::assertNothingSent(); expect(User::query()->where('email', 'bot-target@example.test')->exists())->toBeFalse(); });