CluPilotCloud/tests/Feature/ContactRequestTest.php

152 lines
5.5 KiB
PHP

<?php
use App\Mail\ContactRequestMail;
use Illuminate\Support\Facades\Mail;
/**
* Das Anfrageformular der öffentlichen Website.
*
* Es steht offen im Internet und verschickt eine Mail — die Grenzen sind hier
* das Wesentliche, nicht die Felder.
*/
beforeEach(function () {
Mail::fake();
});
it('zeigt das Formular', function () {
$this->get(route('contact'))
->assertOk()
->assertSee('Sprechen Sie uns an.')
->assertSee('Anfrage senden');
});
it('stellt beim Thema Enterprise die Frage, um die es geht', function () {
$this->get(route('contact', ['thema' => 'enterprise']))
->assertOk()
->assertSee('Eine eigene Maschine.')
// Nicht ein leeres Feld hinstellen: wer hier landet, kam über den Knopf
// unter den Paketen, und die zwei Zahlen entscheiden das Angebot.
->assertSee('Wie viel Speicher brauchen Sie', false);
});
it('fällt bei einem erfundenen Thema auf die allgemeine Fassung zurück', function () {
// ?thema= steht in der Adresse und ist damit von jedem frei wählbar.
$this->get(route('contact', ['thema' => '<script>']))
->assertOk()
->assertSee('Sprechen Sie uns an.');
});
it('schickt die Anfrage an das Haus und lässt die Antwort an den Fragenden gehen', function () {
$this->post(route('contact.send'), [
'company' => 'Kanzlei Muster',
'name' => 'Anna Muster',
'email' => 'anna@kanzlei-muster.at',
'phone' => '+43 1 2345678',
'message' => 'Wir haben 40 Mitarbeiter und brauchen etwa 400 GB.',
'topic' => 'enterprise',
])->assertRedirect(route('contact'));
Mail::assertQueued(ContactRequestMail::class, function (ContactRequestMail $mail) {
$envelope = $mail->envelope();
// Der Punkt der ganzen Mail: der Betreiber drückt „Antworten" und
// schreibt der Person, nicht sich selbst.
expect($envelope->replyTo[0]->address)->toBe('anna@kanzlei-muster.at');
// Gesendet wird AUS dem eigenen Haus, nicht aus der fremden Domain —
// sonst scheitert die Mail an SPF und DKIM und landet im Spam.
expect($envelope->from->address)->not->toBe('anna@kanzlei-muster.at');
// Betreff trägt Thema und Absender, damit die Postfachliste allein
// schon sagt, worum es geht.
expect($envelope->subject)->toBe('Anfrage: eigene Maschine — Kanzlei Muster');
return true;
});
});
it('nimmt den Namen in den Betreff, wenn keine Firma angegeben ist', function () {
$this->post(route('contact.send'), [
'name' => 'Bernd Beispiel',
'email' => 'bernd@example.at',
'message' => 'Ich hätte da eine Frage zu Ihren Paketen.',
]);
Mail::assertQueued(ContactRequestMail::class, fn (ContactRequestMail $mail) => $mail->envelope()->subject === 'Anfrage über die Website — Bernd Beispiel');
});
it('bestätigt sichtbar und zeigt das Formular danach nicht mehr', function () {
$this->post(route('contact.send'), [
'name' => 'Anna Muster',
'email' => 'anna@example.at',
'message' => 'Bitte melden Sie sich bei mir.',
]);
$this->followingRedirects()
->post(route('contact.send'), [
'name' => 'Anna Muster',
'email' => 'anna@example.at',
'message' => 'Bitte melden Sie sich bei mir.',
])
->assertOk()
->assertSee('Ihre Anfrage ist da.')
// Ein Formular, das nach dem Absenden weiter dasteht, lädt zum zweiten
// Absenden ein.
->assertDontSee('Anfrage senden');
});
it('verlangt Name, Adresse und Nachricht', function () {
$this->post(route('contact.send'), [])
->assertSessionHasErrors(['name', 'email', 'message']);
Mail::assertNothingQueued();
});
it('lässt eine Nachricht aus zwei Wörtern nicht durch', function () {
$this->post(route('contact.send'), [
'name' => 'Anna', 'email' => 'anna@example.at', 'message' => 'Hallo',
])->assertSessionHasErrors(['message']);
Mail::assertNothingQueued();
});
it('verwirft, was in den Honigtopf getappt ist', function () {
// Das Feld ist im Browser nicht zu sehen. Wer es ausfüllt, ist kein Mensch.
$this->post(route('contact.send'), [
'name' => 'Robot', 'email' => 'robot@example.com',
'message' => 'Kaufen Sie unsere Backlinks, sehr günstig.',
'website' => 'http://spam.example.com',
])->assertSessionHasErrors(['website']);
Mail::assertNothingQueued();
});
it('bremst den Versand, statt ihn offen stehen zu lassen', function () {
// Ein Formular, das ohne Bremse Mail verschickt, ist ein Versandweg für
// jeden, der es findet. Fünf in zehn Minuten, danach 429.
$payload = ['name' => 'Anna', 'email' => 'anna@example.at', 'message' => 'Eine ganz normale Anfrage.'];
for ($i = 0; $i < 5; $i++) {
$this->post(route('contact.send'), $payload)->assertRedirect();
}
$this->post(route('contact.send'), $payload)->assertStatus(429);
Mail::assertQueuedCount(5);
});
it('trägt fremdes Markup nicht in die Mail, die unsere Adresse als Absender hat', function () {
$this->post(route('contact.send'), [
'name' => 'Anna Muster',
'email' => 'anna@example.at',
'message' => "Guten Tag\n<script>alert('x')</script>\nMit freundlichen Grüßen",
]);
Mail::assertQueued(ContactRequestMail::class, function (ContactRequestMail $mail) {
$html = $mail->render();
return ! str_contains($html, "<script>alert('x')</script>")
&& str_contains($html, '&lt;script&gt;');
});
});