If you’ve ever wondered how search engines like Google actually find and index your Laravel-powered website, the answer often lies in a well-structured XML sitemap. Without one, even your best content might stay hidden in the shadows. The good news? Generating a dynamic XML sitemap in Laravel is easier than you think.
In this guide, I’ll walk you through a step-by-step process to build a dynamic XML sitemap in Laravel from any list of links—helping your site become more SEO-friendly and crawlable in just minutes.
Step 1: Create a Controller
We’ll start by creating a SitemapController
to generate the XML response.
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Response;
class SitemapController extends Controller
{
public function index()
{
// Example list of links (this can come from DB or config)
$links = [
['url' => url('/'), 'updated_at' => now()],
['url' => url('/about'), 'updated_at' => now()->subDays(2)],
['url' => url('/contact'), 'updated_at' => now()->subDays(5)],
];
$content = view('sitemap', compact('links'));
return response($content, 200)
->header('Content-Type', 'application/xml');
}
}
You can extend this controller to fetche links from your database (e.g., posts, products, categories) automatically instead of a manual list like below:
<?php
namespace App\Http\Controllers;
use App\Models\Page;
use Illuminate\Http\Response;
class SitemapController extends Controller
{
public function index()
{
// Example list of links (this can come from DB or config)
$links = Page::all();
$content = view('sitemap', compact('links'));
return response($content, 200)
->header('Content-Type', 'application/xml');
}
}
Alternative Solution
If you don’t want to create controller, you can add this code directly to routes/web.php
route as follows:
<?php
use App\Models\Page;
use Illuminate\Support\Facades\Artisan;
use Illuminate\Support\Facades\Route;
Route::get('/sitemap.xml', function () {
$links = Page::all();
$content = view('sitemap', [
'links' => $links,
]);
return response($content, 200)
->header('Content-Type', 'application/xml');
});
Step 2: Create the Blade View
Create a new file at resources/views/sitemap.blade.php
and paste the following code:
{!! '<?xml version="1.0" encoding="UTF-8"?>' !!}
<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9">
@foreach ($links as $link)
<url>
<loc>{{ $link->url }}</loc>
<lastmod>{{ \Carbon\Carbon::parse($link->updated_at)->toAtomString() }}</lastmod>
<changefreq>weekly</changefreq>
<priority>0.8</priority>
</url>
@endforeach
</urlset>
Note: We use {!! '<?xml version="1.0" encoding="UTF-8"?>' !!}
because Blade treats <?xml ... ?>
as a PHP tag, which causes a syntax error.
Step 3: Add the Route
Open routes/web.php
and add:
use App\Http\Controllers\SitemapController;
Route::get('/sitemap.xml', [SitemapController::class, 'index']);
Note: If you have directly added the code of sitemap to this file, then you can skip this step.
Step 4: Test Your Sitemap
Now, visit:
https://yourapp.com/sitemap.xml
You should see a valid sitemap like this:
<?xml version="1.0" encoding="UTF-8"?>
<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9">
<url>
<loc>https://yourapp.com/</loc>
<lastmod>2025-09-17T09:10:00+00:00</lastmod>
<changefreq>weekly</changefreq>
<priority>0.8</priority>
</url>
<url>
<loc>https://yourapp.com/about</loc>
<lastmod>2025-09-15T09:10:00+00:00</lastmod>
<changefreq>weekly</changefreq>
<priority>0.8</priority>
</url>
</urlset>
Conclusion
With just a few steps, you’ve created a dynamic XML sitemap in Laravel. You can extend this by fetching links from your database (e.g., blog posts, products, categories) instead of a static list.
This setup ensures your site is search engine friendly and keeps your content crawlable and indexable.