Skip to content

Commit 277a73b

Browse files
committed
minor #1814 [Site] Add robots.txt & sitemap.xml (smnandre)
This PR was squashed before being merged into the 2.x branch. Discussion ---------- [Site] Add robots.txt & sitemap.xml Commits ------- 446ff5c [Site] Add robots.txt & sitemap.xml
2 parents 1f59f55 + 446ff5c commit 277a73b

File tree

7 files changed

+176
-1
lines changed

7 files changed

+176
-1
lines changed

ux.symfony.com/php.ini

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,4 @@
11
allow_url_include=off
2-
assert.active=off
32
display_errors=off
43
display_startup_errors=off
54
max_execution_time=30

ux.symfony.com/src/Controller/MainController.php

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
use App\Model\RecipeFileTree;
1515
use App\Service\UxPackageRepository;
1616
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
17+
use Symfony\Component\HttpFoundation\Request;
1718
use Symfony\Component\HttpFoundation\Response;
1819
use Symfony\Component\Routing\Attribute\Route;
1920

@@ -29,4 +30,13 @@ public function homepage(UxPackageRepository $packageRepository): Response
2930
'recipeFileTree' => new RecipeFileTree(),
3031
]);
3132
}
33+
34+
#[Route(path: '/robots.txt', name: 'app_robots')]
35+
public function __invoke(Request $request): Response
36+
{
37+
$response = $this->render('robots.txt.twig');
38+
$response->headers->set('Content-Type', 'text/plain');
39+
40+
return $response;
41+
}
3242
}
Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <[email protected]>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespace App\Controller;
13+
14+
use App\Service\LiveDemoRepository;
15+
use App\Service\UxPackageRepository;
16+
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
17+
use Symfony\Component\HttpFoundation\Request;
18+
use Symfony\Component\HttpFoundation\Response;
19+
use Symfony\Component\Routing\Attribute\Route;
20+
use Symfony\Component\Routing\Generator\UrlGeneratorInterface;
21+
22+
final class SitemapController extends AbstractController
23+
{
24+
public function __construct(
25+
private readonly UxPackageRepository $uxPackageRepository,
26+
private readonly LiveDemoRepository $liveDemoRepository,
27+
) {
28+
}
29+
30+
#[Route(path: '/sitemap.xml', name: 'app_sitemap')]
31+
public function __invoke(Request $request): Response
32+
{
33+
$response = $this->render('sitemap.xml.twig', [
34+
'urls' => $this->getSitemapUrls(),
35+
]);
36+
$response->headers->set('Content-Type', 'application/xml');
37+
38+
return $response;
39+
}
40+
41+
/**
42+
* @return iterable<string>
43+
*/
44+
private function getSitemapUrls(): iterable
45+
{
46+
// Static pages
47+
yield $this->generateAbsoluteUrl('app_homepage');
48+
yield $this->generateAbsoluteUrl('app_packages');
49+
yield $this->generateAbsoluteUrl('app_icons');
50+
yield $this->generateAbsoluteUrl('app_demos');
51+
yield $this->generateAbsoluteUrl('app_changelog');
52+
53+
// UX Packages
54+
foreach ($this->uxPackageRepository->findAll() as $package) {
55+
yield $this->generateAbsoluteUrl($package->getRoute());
56+
}
57+
58+
// Live Demos
59+
foreach ($this->liveDemoRepository->findAll() as $demo) {
60+
yield $this->generateAbsoluteUrl($demo->getRoute());
61+
}
62+
}
63+
64+
private function generateAbsoluteUrl(string $route, array $parameters = []): string
65+
{
66+
return $this->generateUrl($route, $parameters, UrlGeneratorInterface::ABSOLUTE_URL);
67+
}
68+
}
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
User-agent: *
2+
Disallow:
3+
4+
Sitemap: {{ url('app_sitemap') }}
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9" xmlns:xhtml="http://www.w3.org/1999/xhtml">
3+
{%- for url in urls ~%}
4+
<url>
5+
<loc>{{ url }}</loc>
6+
</url>
7+
{%- endfor ~%}
8+
</urlset>
Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <[email protected]>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespace App\Tests\Functional;
13+
14+
use Symfony\Bundle\FrameworkBundle\Test\KernelTestCase;
15+
use Zenstruck\Browser\Test\HasBrowser;
16+
17+
class RobotsTest extends KernelTestCase
18+
{
19+
use HasBrowser;
20+
21+
public function testSitemapContainsPages(): void
22+
{
23+
$browser = $this->browser([], [
24+
'HTTP_HOST' => 'ux.symfony.com',
25+
])
26+
->visit('/robots.txt')
27+
->assertSuccessful()
28+
->assertContentType('text/plain');
29+
$robot = $browser->content();
30+
31+
$this->assertStringStartsWith("User-agent: *\nDisallow:\n", $robot);
32+
$this->assertStringContainsString('Sitemap: http://ux.symfony.com/sitemap.xml', $robot);
33+
}
34+
}
Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <[email protected]>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespace App\Tests\Functional;
13+
14+
use App\Service\LiveDemoRepository;
15+
use App\Service\UxPackageRepository;
16+
use Symfony\Bundle\FrameworkBundle\Test\KernelTestCase;
17+
use Symfony\Component\Routing\Generator\UrlGeneratorInterface;
18+
use Zenstruck\Browser\Test\HasBrowser;
19+
20+
class SitemapTest extends KernelTestCase
21+
{
22+
use HasBrowser;
23+
24+
public function testSitemapContainsPages(): void
25+
{
26+
$browser = $this->browser()
27+
->visit('/sitemap.xml')
28+
->assertSuccessful()
29+
->assertXml()
30+
;
31+
32+
$sitemap = $browser->content();
33+
foreach ($this->getSmokeTests() as $url) {
34+
$this->assertStringContainsString('<loc>'.$url.'</loc>', $sitemap);
35+
}
36+
}
37+
38+
private function getSmokeTests(): \Generator
39+
{
40+
$router = self::bootKernel()->getContainer()->get('router');
41+
42+
$demoRepository = new LiveDemoRepository();
43+
foreach ($demoRepository->findAll() as $demo) {
44+
yield $demo->getRoute() => $router->generate($demo->getRoute(), [], UrlGeneratorInterface::ABSOLUTE_URL);
45+
}
46+
47+
$packageRepository = new UxPackageRepository();
48+
foreach ($packageRepository->findAll() as $package) {
49+
yield $package->getRoute() => $router->generate($package->getRoute(), [], UrlGeneratorInterface::ABSOLUTE_URL);
50+
}
51+
}
52+
}

0 commit comments

Comments
 (0)