Sitemap search engine friendly in Laravel

postat acum 11 luni de Stefanescu Mihai in categorie iNoob

Cu ceva timp in urma (acum cativa ani) motoarele de cautare (ex: Google) au recomandat sa facem submit sitemap-urilor astfel incat indexarea site-urilor sa fie mai simpla si rapida.

In clipa de fata exista pareri si pareri cum ca sitemap-ul nu mai este atat de important in prezent, dar eu sunt de parere ca nu poate strica sa dai submit unui sitemap.

Ce este un sitemap?

Daca nu cunosti termenul, Google a dat aceasta definitie:

A sitemap is a file where you can list the web pages of your site to tell Google and other search engines about the organization of your site content. Search engine web crawlers like Googlebot read this file to more intelligently crawl your site.

Ne mai dau si urmatoarele motive de a face submit unui sitemap:

  • Site-ul este foarte mare, iar crawlerii Google pot sari peste anumite pagini din site.

  • Site-ul are o arhiva foarte mare cu link-uri izolate sau pentru care nu exista link-uri atat de usor accesibile

  • Site-ul are mult continut media.

Poate ca site-ul tau nu se incadreaza in aceste criterii, dar tot nu ar strica sa faci submit unui sitemap.

Protocolul sitemap

Pe site-ul oficial se regasesc toate informatiile referitoare la structura unui fisier sitemap, dar totusi am sa va pun si aici un mic exemplu:

<?xml version="1.0" encoding="UTF-8"?>
<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9">
   <url>
      <loc>http://www.invata-programare.ro/</loc>
      <lastmod>2005-01-01</lastmod>
      <changefreq>monthly</changefreq>
      <priority>0.8</priority>
   </url>
</urlset> 

Din ce se poate observa sitemap-ul este un simplu xml ce contine tag-ul <url> pentru fiecare pagina din site-ul tau.

Un singur sitemap poate contine in jud de 50000 link-uri, dar daca aveti nevoie le puteti separa in mai multe fixiere, iar apoi sa le includeti intr-un fisier de index.

Acest fisier ar trebuii sa arate in acest mod:

<?xml version="1.0" encoding="UTF-8"?>
<sitemapindex xmlns="http://www.sitemaps.org/schemas/sitemap/0.9">
   <sitemap>
      <loc>http://www.invata-programare.ro/sitemap1.xml.gz</loc>
      <lastmod>2004-10-01T18:23:17+00:00</lastmod>
   </sitemap>
   <sitemap>
      <loc>http://www.invata-programare.ro/sitemap2.xml.gz</loc>
      <lastmod>2005-01-01</lastmod>
   </sitemap>
</sitemapindex>

In tag-ul <loc> punem locatia fisierului xml, intr-o maniera similara cu <url>

Construirea unui Controller pentru Sitemap

In acest articol voi considera ca voi crea sitemap pentru articole pe blog, categoriile blogului si articole video. Fiecar dintre acestea va avea proriul sitemap, iar mai apoi vor fi apelate in fisierul de index.

Pentru inceput hai sa facem un controller pentru sitemap:

php artisan make:controller SitemapController

Acum hai sa deschidem acest fisier si sa facem un fisier de index.

Crearea indexului

Hai sa scriem o metoda ce ne va genera XML-ul necesar:

public function index()
{
  $post = Post::active()->orderBy('updated_at', 'desc')->first();
  $video = Video::active()->orderBy('updated_at', 'desc')->first();

  return response()->view('sitemap.index', [
      'post' => $post,
      'video' => $video,
  ])->header('Content-Type', 'text/xml');
}

Atentie, in sitemap trebuie sa avem si timestamp-urile articolelor, astfel incat crawlerele sa stie daca au aparut modificari in continut.

Probabil nu sunteti obisnuiti cu acest tip de return, ci doar cu return-ul unui view in modul clasic. In acest mod returnez un view caruia ii setez headerul de text/xml. View-ul mei sitemap.index arata in acest mod:

<?php echo '<?xml version="1.0" encoding="UTF-8"?>'; ?>

<sitemapindex xmlns="http://www.sitemaps.org/schemas/sitemap/0.9">
    <sitemap>
        <loc>https://invata-programare.ro/sitemap/posts</loc>
        <lastmod>{{ $post->publishes_at->tz('UTC')->toAtomString() }}</lastmod>
    </sitemap>
    <sitemap>
        <loc>https://invata-programare.ro/sitemap/categories</loc>
        <lastmod>{{ $post->publishes_at->tz('UTC')->toAtomString() }}</lastmod>
    </sitemap>
    <sitemap>
        <loc>https://invata-programare.ro/sitemap/podcasts</loc>
        <lastmod>{{ $podcast->publishes_at->tz('UTC')->toAtomString() }}</lastmod>
    </sitemap
</sitemapindex>

In acest view am sa folosesc Carbon pentru a afisa data in UTC si in formatul corect.

Crearea sitemap-urilor

Urmatorul pas este crearea fiecarei pagini pentru sitemap-uri. Trebuie sa facem 3 metode noi si foarte similare in controller.

public function posts()
{
    $posts = Post::active()->where('category_id', '!=', 21)->get();
    return response()->view('sitemap.posts', [
        'posts' => $posts,
    ])->header('Content-Type', 'text/xml');
}

public function categories()
{
    $categories = Category::all();
    return response()->view('sitemap.categories', [
        'categories' => $categories,
    ])->header('Content-Type', 'text/xml');
}

public function videos()
{
    $videos = Video::active()->orderBy('updated_at', 'desc')->get();
    return response()->view('sitemap.videos', [
        'videos' => $videos,
    ])->header('Content-Type', 'text/xml');
}

O data ce am facut aceste metode trebuie sa facem si view-ul pentru fiecare. Iata mai jos un exemplu de view:

<?php echo '<?xml version="1.0" encoding="UTF-8"?>'; ?>
<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9">
    @foreach ($posts as $post)
        <url>
            <loc>https://invata-programare.ro/{{ $post->uri }}</loc>
            <lastmod>{{ $post->publishes_at->tz('UTC')->toAtomString() }}</lastmod>
            <changefreq>weekly</changefreq>
            <priority>0.6</priority>
        </url>
    @endforeach
</urlset>

O data ce am ajuns aici mai trebuie sa facem un singur lucru, rutele:

Route::get('/sitemap', '[email protected]');
Route::get('/sitemap/posts', '[email protected]');
Route::get('/sitemap/categories', '[email protected]');
Route::get('/sitemap/videos', '[email protected]');

Concluzie

Din ce se poate observa, construirea unui sitemap in laravel este relativ simpla, mai ales daca ai un site cu o structura relativ simpla cum am eu in exemplul din articol.

Sunt un tanar programator din Bucuresti ce lucreaza in PHP/Mysql (MySqli/PDO), Laravel, CodeIgniter, MySQL, PostgreSQL, Wordpress, HTML5/CSS3, Sass, Photoshop si multe altele.
Google+ Community Facebook Group