R4.3: Karten-Metadaten-Logik als PressRelease-Praesentations-Helper
localizedCategoryName/cardImageUrl/teaserText/wordCount/readTimeMinutes/ compactPublishedLabel ersetzen die 5x kopierte @php-Logik der Kartenkomponenten; Lesezeit-Formel vereinheitlicht (ceil -> round in HomePageData-Spotlight). Tests: Web/PressReleaseCardHelpersTest. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
parent
56ea3d0169
commit
813cbd2e18
4 changed files with 137 additions and 3 deletions
63
tests/Feature/Web/PressReleaseCardHelpersTest.php
Normal file
63
tests/Feature/Web/PressReleaseCardHelpersTest.php
Normal file
|
|
@ -0,0 +1,63 @@
|
|||
<?php
|
||||
|
||||
use App\Enums\Portal;
|
||||
use App\Models\Category;
|
||||
use App\Models\PressRelease;
|
||||
|
||||
test('localizedCategoryName resolves the current locale with fallback to the first translation', function () {
|
||||
$category = Category::factory()->create(['portal' => Portal::Businessportal24]);
|
||||
$category->translations()->create(['locale' => 'de', 'name' => 'Energie & Klima', 'slug' => 'energie-klima']);
|
||||
$category->translations()->create(['locale' => 'en', 'name' => 'Energy & Climate', 'slug' => 'energy-climate']);
|
||||
|
||||
$release = PressRelease::factory()->for($category)->create();
|
||||
$release->load('category.translations');
|
||||
|
||||
app()->setLocale('de');
|
||||
expect($release->localizedCategoryName())->toBe('Energie & Klima');
|
||||
|
||||
app()->setLocale('en');
|
||||
expect($release->localizedCategoryName())->toBe('Energy & Climate');
|
||||
|
||||
// Fallback: Sprache ohne Übersetzung → erste vorhandene.
|
||||
app()->setLocale('fr');
|
||||
expect($release->localizedCategoryName())->toBe('Energie & Klima');
|
||||
|
||||
app()->setLocale('de');
|
||||
});
|
||||
|
||||
test('teaserText strips tags, squishes whitespace and limits length', function () {
|
||||
$release = PressRelease::factory()->create([
|
||||
'text' => "<p>Erster Absatz.</p>\n<p>Zweiter Absatz mit <strong>Auszeichnung</strong>.</p>",
|
||||
]);
|
||||
|
||||
expect($release->teaserText())->toBe('Erster Absatz. Zweiter Absatz mit Auszeichnung.')
|
||||
->and($release->teaserText(13))->toBe('Erster Absatz...');
|
||||
});
|
||||
|
||||
test('readTimeMinutes rounds at 200 words per minute with a minimum of one', function () {
|
||||
$short = PressRelease::factory()->create(['text' => 'Nur wenige Worte.']);
|
||||
$long = PressRelease::factory()->create(['text' => implode(' ', array_fill(0, 450, 'Wort'))]);
|
||||
|
||||
expect($short->wordCount())->toBe(3)
|
||||
->and($short->readTimeMinutes())->toBe(1)
|
||||
->and($long->readTimeMinutes())->toBe(2);
|
||||
});
|
||||
|
||||
test('compactPublishedLabel formats today, yesterday and older dates', function () {
|
||||
$today = PressRelease::factory()->create(['published_at' => now()->setTime(9, 30)]);
|
||||
$yesterday = PressRelease::factory()->create(['published_at' => now()->subDay()]);
|
||||
$older = PressRelease::factory()->create(['published_at' => now()->parse('2026-03-05 08:00')]);
|
||||
$unpublished = PressRelease::factory()->create(['published_at' => null]);
|
||||
|
||||
expect($today->compactPublishedLabel())->toBe('09:30')
|
||||
->and($yesterday->compactPublishedLabel())->toBe(__('web.shared.yesterday'))
|
||||
->and($older->compactPublishedLabel())->toBe($older->published_at->isoFormat('D. MMM'))
|
||||
->and($unpublished->compactPublishedLabel())->toBeNull();
|
||||
});
|
||||
|
||||
test('cardImageUrl is null for releases without images', function () {
|
||||
$release = PressRelease::factory()->create();
|
||||
$release->load('images');
|
||||
|
||||
expect($release->cardImageUrl())->toBeNull();
|
||||
});
|
||||
Loading…
Add table
Add a link
Reference in a new issue