web: E9 und E10 entschieden — Zuordnung aktiv, eine Adresse je statischer Seite, Hub-Portalseiten leiten weiter
E9: Kategorie-Zuordnung wie vorgeschlagen übernommen, Zuordnung ist standardmäßig an (CANONICAL_ASSIGNMENT_ENABLED). Auf der Dev-Kopie verifiziert: Kopie trägt rel=canonical auf die Erstquelle und fällt aus der Sitemap ihres Portals. E10: faq, hilfe, gute-pressemitteilung, die vier Transparenzseiten und die API-Doku lagen auf allen drei Hosts mit identischem Text und je eigenem Self-Canonical. Jetzt führt presseecho die Informationsseiten, der Hub die API-Doku; Sitemap und llms.txt nennen nur die führende Adresse. Rechtstexte (Impressum, Datenschutz, AGB, Richtlinien, Meldeweg, Kündigung) bleiben bewusst je Host — jede Domain ist ein eigenes Angebot mit eigener Anbieterkennzeichnung. Bei der Erreichbarkeitsprüfung des Hubs gefunden und behoben: /de/preise, /de/veroeffentlichen, /de/newsrooms und /de/suche wurden unter pressekonto.com mit dem Branding von businessportal24 ausgeliefert (der Portal-Kontext fällt dort darauf zurück) — jetzt 301 auf presseecho, die Transparenz-Navigation verlinkt direkt dorthin. /de/kontakt und /de/ueber-uns sprangen über /de auf die Startseite, jetzt in einem Schritt. Der Self-Canonical kommt jetzt aus dem aufgerufenen Host; Portal-Inhalte, die über den Hub laufen, behalten ihr Portal (webPortalContextApplied). Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
parent
ee267c622e
commit
4c17a17254
18 changed files with 434 additions and 17 deletions
74
tests/Feature/Web/HubPortalPageRedirectTest.php
Normal file
74
tests/Feature/Web/HubPortalPageRedirectTest.php
Normal file
|
|
@ -0,0 +1,74 @@
|
|||
<?php
|
||||
|
||||
use App\Enums\Portal;
|
||||
use App\Models\Category;
|
||||
use Tests\TestCase;
|
||||
|
||||
test('portal-only pages redirect from the hub to the leading portal', function (string $path) {
|
||||
/** @var TestCase $this */
|
||||
$this->get('https://pressekonto.test'.$path)
|
||||
->assertStatus(301)
|
||||
->assertRedirect('https://presseecho.test'.$path);
|
||||
})->with(['/de/preise', '/de/veroeffentlichen', '/de/newsrooms', '/de/suche', '/en/preise']);
|
||||
|
||||
test('the portals keep serving those pages themselves', function (string $host) {
|
||||
/** @var TestCase $this */
|
||||
$this->get($host.'/de/preise')->assertSuccessful();
|
||||
})->with(['https://presseecho.test', 'https://businessportal24.test']);
|
||||
|
||||
test('shared info pages name one leading host on all three domains', function (string $host) {
|
||||
/** @var TestCase $this */
|
||||
// Anhang 2, E10: Informationsseiten liegen dreifach vor — presseecho
|
||||
// führt, die API-Doku gehört zum Hub.
|
||||
$this->get($host.'/de/faq')->assertSuccessful()
|
||||
->assertSee('<link rel="canonical" href="https://presseecho.test/de/faq">', false);
|
||||
$this->get($host.'/de/was-kostet-eine-pressemitteilung')->assertSuccessful()
|
||||
->assertSee('<link rel="canonical" href="https://presseecho.test/de/was-kostet-eine-pressemitteilung">', false)
|
||||
->assertSee('<meta property="og:url" content="https://presseecho.test/de/was-kostet-eine-pressemitteilung">', false);
|
||||
$this->get($host.'/de/api')->assertSuccessful()
|
||||
->assertSee('<link rel="canonical" href="https://pressekonto.test/de/api">', false);
|
||||
})->with(['https://pressekonto.test', 'https://presseecho.test', 'https://businessportal24.test']);
|
||||
|
||||
test('legal pages stay with their own domain', function (string $host, string $path) {
|
||||
/** @var TestCase $this */
|
||||
// Jede Domain ist ein eigenes Angebot: Impressum, AGB, Datenschutz,
|
||||
// Richtlinien und Meldeweg gehören zu dem Host, auf dem sie stehen.
|
||||
$this->get($host.$path)->assertSuccessful()
|
||||
->assertSee('<link rel="canonical" href="'.$host.$path.'">', false);
|
||||
})->with([
|
||||
['https://pressekonto.test', '/de/impressum'],
|
||||
['https://businessportal24.test', '/de/agb'],
|
||||
['https://businessportal24.test', '/de/datenschutz'],
|
||||
['https://presseecho.test', '/de/melden'],
|
||||
['https://businessportal24.test', '/de/richtlinien'],
|
||||
]);
|
||||
|
||||
test('the english edition keeps the leading host too', function () {
|
||||
/** @var TestCase $this */
|
||||
$this->get('https://businessportal24.test/en/hilfe')->assertSuccessful()
|
||||
->assertSee('<link rel="canonical" href="https://presseecho.test/en/hilfe">', false);
|
||||
});
|
||||
|
||||
test('the retired contact and about pages redirect to the home page in one hop', function (string $host, string $target) {
|
||||
/** @var TestCase $this */
|
||||
$this->get($host.'/de/kontakt')->assertStatus(301)->assertRedirect($target);
|
||||
$this->get($host.'/de/ueber-uns')->assertStatus(301)->assertRedirect($target);
|
||||
})->with([
|
||||
// Auf dem Hub liegt die Startseite unter `/` — der frühere Weg über
|
||||
// `/de` war eine zweite Weiterleitung.
|
||||
['https://pressekonto.test', 'https://pressekonto.test'],
|
||||
['https://presseecho.test', 'https://presseecho.test/de'],
|
||||
]);
|
||||
|
||||
test('portal content served through the hub keeps the portal as canonical', function () {
|
||||
/** @var TestCase $this */
|
||||
// Die Ausgabe-Routen gelten für alle Hosts, deshalb sind Kategorien und
|
||||
// Meldungen auch unter pressekonto.com erreichbar. Sie rendern dort das
|
||||
// Portal — der Canonical muss dorthin zeigen, nie auf den Hub.
|
||||
$category = Category::factory()->create(['portal' => Portal::Both]);
|
||||
$category->translations()->create(['locale' => 'de', 'name' => 'Handel', 'slug' => 'handel']);
|
||||
|
||||
$this->get('https://pressekonto.test/de/category/handel')->assertSuccessful()
|
||||
->assertSee('<link rel="canonical" href="https://businessportal24.test/de/category/handel">', false)
|
||||
->assertDontSee('<link rel="canonical" href="https://pressekonto.test/de/category/handel">', false);
|
||||
});
|
||||
|
|
@ -263,7 +263,9 @@ test('the good-release help page explains the check without selling anything', f
|
|||
$body = Str::between($response->getContent(), 'class="pm-body', 'aria-labelledby="partner-heading"');
|
||||
expect($body)->not->toContain('/preise')->not->toContain('Credits');
|
||||
|
||||
// Aus dem Hilfe-Center und der Sitemap erreichbar.
|
||||
// Aus dem Hilfe-Center erreichbar; in der Sitemap steht sie beim
|
||||
// führenden Host (Anhang 2, E10) — presseecho, nicht businessportal24.
|
||||
$this->get('https://businessportal24.test/de/hilfe')->assertSee('/de/gute-pressemitteilung', false);
|
||||
$this->get('https://businessportal24.test/sitemap.xml')->assertSee('/de/gute-pressemitteilung', false);
|
||||
$this->get('https://presseecho.test/sitemap.xml')->assertSee('/de/gute-pressemitteilung', false);
|
||||
$this->get('https://businessportal24.test/sitemap.xml')->assertDontSee('/de/gute-pressemitteilung', false);
|
||||
});
|
||||
|
|
|
|||
|
|
@ -123,6 +123,9 @@ test('the pages are linked from the pricing page, the help centre and the sitema
|
|||
$this->get('https://presseecho.test/llms.txt')->assertSuccessful()
|
||||
->assertSee('/de/pressemitteilung-kostenlos-veroeffentlichen', false);
|
||||
|
||||
// Die Seiten liegen auf allen drei Hosts; in der Sitemap steht nur die
|
||||
// führende Adresse (Anhang 2, E10) — beim Hub bleibt die API-Doku.
|
||||
$this->get('https://pressekonto.test/sitemap.xml')->assertSuccessful()
|
||||
->assertSee('<loc>https://pressekonto.test/de/pressemitteilung-loeschen-oder-aendern-lassen</loc>', false);
|
||||
->assertDontSee('/de/pressemitteilung-loeschen-oder-aendern-lassen', false)
|
||||
->assertSee('<loc>https://pressekonto.test/de/api</loc>', false);
|
||||
});
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue