Атрибут rel = "canonical". Посилання на канонічні сторінки

  1. Для чого потрібен rel = "canonical"
  2. Проблема з rel = "canonical" в плагіні All in One SEO Pack
  3. Функція rel_canonical ()
  4. Помилка в плагіні All in One SEO Pack
  5. Посилання з атрибутами prev і next
  6. Одночасне використання rel = "canonical" і мета-тега robots
  7. Як правильно вивести посилання на канонічні сторінки WordPress

Всім привіт! Сьогодні на seo-mayak.com ми будемо розбирати атрибут rel = "canonical". Розглянемо його, так би мовити, під різними кутами, проведемо деякі порівняння і звичайно трохи попрацюємо з PHP.

За минулих пару місяців, я отримав безліч листів з різними проханнями і пропозиціями. Якщо комусь не відповіли, прошу не судити строго. На всіх мене все одно не вистачить!

Підбираючи тему для майбутньої статті, я погортав пошту і зрозумів, що веб-майстрів став сильно хвилювати тег canonical. Правильно його буде називати атрибутом, тому слово «тег», стосовно rel = "canonical", я більше використовувати не стану.

Так ось, після статті Олександра Борисова в якій він описав проблему з canonical в плагіні All in One SEO Pack , Всі кинулися шукати якусь інформацію, щодо даного атрибута, а її насправді не так багато.

Є звичайно мануал Google або довідка Яндекса, де досить коротко описується взаємодія атрибута з пошуковими алгоритмами. Пояснюється як роботи розуміють rel = "canonical" і як правильно його застосовуватимуть.

Почитавши деякі статті по темі, я зрозумів, що конкретних інструкцій щодо самостійного впровадження rel = "canonical" на сторінки сайту, просто немає і веб-майстри майже поголовно використовують плагіни, які завжди підносять якісь сюрпризи.

Ось і стрибає народ з плагіна на плагін, так реально і не розібравшись в принципах роботи rel = "canonical". А принцип простий. Вихідна сторінка повинна залишити свій слід на всіх передбачуваних копіях, щоб у пошукового робота не було ні найменшого приводу індексувати дубль сторінки.

Вихідна сторінка повинна залишити свій слід на всіх передбачуваних копіях, щоб у пошукового робота не було ні найменшого приводу індексувати дубль сторінки

Загалом атрибут дуже важливий і не завадило б знати, як їм управляти. В кінці статті я приведу функцію, яка візьме на себе посаду адміністратора rel = "canonical".

Але давайте про все по-порядку. Поїхали!

Для чого потрібен rel = "canonical"

Напевно всі знають, що таке дублі сторінок і якої шкоди вони можуть завдати репутації сайту в очах пошукового робота.

Саме для боротьби з дублями сторінок і був розроблений атрибут rel = "canonical". Їм позначають прямі посилання на вихідні (канонічні) сторінки. Позначена посилання виводитися в область шапки сайту, між тегами <head> </ head>.

Робот, зайшовши на певний URL і наткнувшись на посилання з canonical, відразу зрозуміє актуальна ця сторінка канонічної чи це просто дубль, який індексувати не треба. Розглянемо такий приклад.

Припустимо який-небудь блогер вирішить поділиться посиланням на одну з моїх статей, але URL на засланні пропише неправильно:

seo-mayak.com/seo-prodvizhenie/tonkosti-prodvizheniya/skvoznye-ssylki.html?abc

Робот проиндексирует дане посилання, обов'язково пройде за вказаною URL і потрапить на сторінку, в вихідному коді якої він наткнеться на посилання, позначену rel = "canonical":

Робот проиндексирует дане посилання, обов'язково пройде за вказаною URL і потрапить на сторінку, в вихідному коді якої він наткнеться на посилання, позначену rel = canonical:

Тим самим rel = "canonical" захистив мій блог від повного дубля сторінки. Сподіваюся новачкам тепер зрозуміло навіщо потрібен цей атрибут. Йдемо далі.

Проблема з rel = "canonical" в плагіні All in One SEO Pack

Після статті Борисова багато веб-майстри стали відмовлятися від плагіна All in One SEO Pack на користь Platinum Seo Pack. Особисто я вважаю All in One SEO Pack хорошим, функціональним плагіном і відмовлятися від нього через проблеми з rel = "canonical" я б не став.

Platinum Seo Pack оновлюється дуже рідко і не відомо, що буде далі. Розумно було б узагалі не покладати на плагіни функції настройки індексації сайту, а передати такі повноваження шаблоном WordPress, а саме файлу functions.php, але про це трохи пізніше.

Як відомо, при бажанні можна вирішити будь-яке завдання. Проблема плагіна All in One SEO Pack полягає наступних неправильних URL:

seo-mayak.com/seo-prodvizhenie/tonkosti-prodvizheniya/skvoznye-ssylki.html/1234

Це ніщо інше, як посилання на неіснуючу сторінку №1234, статті «Наскрізні посилання» . А якщо пройти за вказаною URL і заглянути в вихідний код сторінки, то в зоні All in One SEO Pack, атрибутом rel = "canonical" буде позначена таке посилання:

Як бачите, посилання не є канонічною і веде на той же неправильний URL. Якщо робот знайде такі неправильні посилання на інших ресурсах світового інтернету, то загроза повної дубля сторінки стане дійсно реальна. Мало того, плагін виводить посилання на наступну або попередню сторінку, у такому ж, неналежному вигляді:

Такі посилання позначаються атрибутами:

rel = "prev" - попередня сторінка
rel = "next" - наступна сторінка

З даними посиланнями ми теж трохи пізніше розберемося.

Ну а поки займемося пошуком вирішення проблеми з атрибутом rel = "canonical" в плагіні All in One SEO Pack. Як завжди на вибір є декілька варіантів:

Спосіб №1. Відмовитися від використання All in One SEO Pack на користь іншого SEO плагіна (не рекомендується).

Спосіб №2. Зняти галочку в пункті «Канонічні URL'и:» і покластися на функціонал WordPress (не рекомендується).

Спосіб №3. Виправити помилку в плагіні All in One SEO Pack (рекомендується)

Спосіб №4. Зняти галочку в пункті «Канонічні URL'и:» і розширити функціонал WordPress (настійно рекомендується).

Перший спосіб по вишеопісиннам причин я розглядати не буду і почну відразу з другого.

Функція rel_canonical ()

Отже, чому я не рекомендую покладатися на функціонал WordPress? Насправді все просто. У CMS WordPress за виведення посилання на канонічну сторінку відповідає функція rel_canonical (), яку можна знайти за адресою wp-includes / link-template.php. Ось вона:

function rel_canonical () {if (! is_singular ()) return; global $ wp_the_query; if (! $ id = $ wp_the_query-> get_queried_object_id ()) return; $ Link = get_permalink ($ id); if ($ page = get_query_var ( 'cpage')) $ link = get_comments_pagenum_link ($ page); echo "<link rel = 'canonical' href = '$ link' /> \ n"; }

Працює дана функція без нарікань, але є одне АЛЕ!

Справа в тому, що функція rel_canonical () спрацьовує лише при активації іншої функції is_singular (), яка об'єднує в собі ще три функції:

is_single () - перевіряє чи є що відкривається страница сторінкою із записом (single).
is_page () - перевіряє чи є що відкривається сторінка статичної сторінкою (page).
is_attachment () - перевіряє чи є що відкривається сторінка сторінкою вкладення (attachment).

Про що це говорить? Це говорить від тому, що при виклику: головної сторінки, сторінок з категоріями, архівів, сторінок міток, авторів, а також будь-яких сторінок пагінацію функція rel_canonical () спрацьовувати не буде.

Чим це загрожує? А загрожує це все темі ж дублями. Наприклад, хтось, на якому-небудь ресурсі, залишить таку посилання:

Робот її проиндексирует, здійснить перехід на мій блог, а в вихідному коді немає посилання на канонічну сторінку і отже роботу нічого не залишиться, як проіндексувати дубль головної сторінки, а потім «нагнути» мої статті в пошуковій видачі. Такі справи!

Функція хороша і забігаючи вперед скажу, що вона нам ще стане в нагоді, а покладатися лише на rel_canonical () не варто.

Помилка в плагіні All in One SEO Pack

Взагалі дивує, чому до мене ще ніхто не перейнявся виправленням помилки в плагін All in One SEO Pack, адже для розробників плагіна це справа нікчемна. Мені ж довелося витратити не мало часу, щоб розібратися у функціях і знайти рішення. А рішення виявилося дуже простими і Ви в цьому зараз самі переконаєтеся.

В текстовому редакторі Notepad ++ відкриваємо файл aioseop_class.php, що знаходиться за адресою wp-content / plugins / all-in-one-seo-pack / aioseop_class.php і шукаємо такий рядок:

$ Link = get_permalink ($ post-> ID);

На момент версії All in One SEO Pack 2.2.4, рядок №2269. Змінюємо функцію get_permalink () на вже знайому нам функцію rel_canonical (). Повинно статися так:

$ Link = rel_canonical ();

І все! Тепер посилання на канонічну сторінку буде виводиться правильно. Можете провести свою ретельну перевірку і відписатися в коментарях.

А вам цікаво, чому розробники плагіна так прорахувалися з функцією get_permalink ()? Ось тут в чому справа. Спочатку, програмісти лепівшіе плагін не врахували, що запис в WordPress може бути розділена на n-кількість сторінок. А далі починається найцікавіше.

Якщо функція get_permalink () приймає параметр $ post-> ID, той повертає посилання на поточний пост в циклі , Знаходячи його по ID .

Так ось друзі програмісти, якщо запис розділена на кілька сторінок і якщо ID записи запитується через властивість об'єкта $ post-> ID (об'єкт-> властивість об'єкта), то буде отриманий URL поточної сторінки в циклі.

Припустимо, що в циклі на даний момент знаходиться сторінка №2033, моєї статті «Мікророзмітки Schema.org» , Яка має такий URL:

seo-mayak.com/seo-prodvizhenie/poiskovye-sistemy/makrorazmetka-schema-org.html/2033

Нещасна функція get_permalink () просто не знає, що їй робити. Адже вона не отримувала ніяких директив, які б вказували їй те, що треба повертати посилання на першу сторінку записи. Ось вона і повертає посилання на неіснуючу сторінку, яка була запрошена на поточний момент.

А ось функція rel_canonical () прекрасно знає, як їй чинити в такій ситуації, тому що вона отримує ID записи за допомогою функції get_queried_object_id (), яка в свою чергу отримує ID записи поза циклом WordPress, через глобальну змінну $ wp_the_query. Такі справи!.

В майбутньому я обов'язково більш детально зупинюся на темі розбиття постів на сторінки, так що підписуєтеся на, буде цікаво.

Настала черга розібратися з посиланнями на наступну і попередню сторінки, помічені атрибутами prev і next.

Посилання з атрибутами prev і next

Питання в тому чи потрібні взагалі такі посилання? Яку смислове навантаження вони несуть з точки зору SEO? А сенс такої. Знову ж таки, якщо запис розділена на кілька сторінок, те використання посилань з атрибутами prev і next цілком виправдано, тому що вони допомагають пошуковому роботу пов'язувати сторінку записи в одне ціле.

Але навіщо зв'язувати сторінку пагінацію, наприклад у категорій або у архівів, адже в 90% випадків посторінкова навігація закривається від індексації. Тому, якщо Ви не пишіть довгих постів, які треба ділити на сторінки, то можете сміливо видаляти посилання на наступну і попередню сторінки.

І ось як це робиться. Відкриваємо файл functions.php, що перебувати в шаблоні і після тега <? Php вставляємо таку функцію:

function mayak_remove_prev_link ($ data) {return false; } Add_filter ( 'aioseop_prev_link', 'mayak_remove_prev_link'); add_filter ( 'aioseop_next_link', 'mayak_remove_prev_link');

Теж саме можна зробити іншим способом. Про «вбивці хуков» remove_action () я Вас вже писав у статті, присвяченій функції wp_head () , Раджу почитати. Йдемо далі.

Одночасне використання rel = "canonical" і мета-тега robots

Ще хочу сказати кілька слів про доцільність одночасного використання атрибута canonical і мета-тега robots.

Розглянемо такий приклад. Робот, читаючи вихідний код, знаходить посилання з атрибутом canonical. Робот зрозумів, що ця сторінка є канонічною, тобто, посилання веде на той же URL.

Але трохи нижче він натикається на мета тег robots, із заборонними директивами:

<Meta name = "robots" content = "noindex, nofollow">

Як надійде робот у такій ситуації?

Тут важливо розуміти, що атрибут rel = "canonical" носить скоріше рекомендаційний характер і безумовно поступається в авторитеті мета-тегу robots. Якщо робот зустріне в мета-тег robots з вищеописаними директивами, то він навіть не стане індексувати посилання з атрибутом canonical, втім як і всі інші елементи на сторінці і отже переходи по посиланнях робот також не здійснюватиме.

Висновок: Використовувати canonical на одній сторінці разом з мета-тегом robots не доцільно. Хоча від присутності посилання з canonical гірше теж не буде. Атрибут може служити у вигляді страхувального варіанту, на випадок, якщо з якої-небудь причини мета-тег robots НЕ буде виведено.

Як правильно вивести посилання на канонічні сторінки WordPress

Отже, нам треба буде доповнити функціонал WordPress і примусити його виводити посилання з rel = "canonical" на всіх сторінках сайту.

Я трохи попрацював над функцією, яка візьме на себе роль адміністратора canonical і буде виводити посилання на канонічні сторінки в належному вигляді і там, де вони і повинні бути.

Увага! Перш, ніж активувати функцію, обов'язково зніміть галочку в плагіні All in One SEO Pack, в пункті «Канонічні URL'и:»

Відкриваємо файл functions.php, що перебувати в папці з темою і в самий початок, після знака <? Php, вставляємо таку функцію:

/ *** Функція виведення rel = "canonical" *** / remove_action ( 'wp_head', 'rel_canonical'); function mayak_wp_canonical () {if (! is_singular ()) return; global $ wp_the_query; if (! $ id = $ wp_the_query-> get_queried_object_id ()) return; $ Link = get_permalink ($ id); if ($ page = get_query_var ( 'cpage')) $ link = get_comments_pagenum_link ($ page); echo "<link rel = 'canonical' href = '$ link' /> \ n"; } Add_action ( 'wp_head', 'mayak_wp_canonical', 3); function mayak_canonical () {if (is_home ()) {$ mayak_chief_link = get_option ( 'home'); $ Mayak_home_link = mayak_link_paged ($ mayak_chief_link); {Echo "". '<Link rel = "canonical" href = "'. $ Mayak_home_link. '" />'."\n "; }} Else if (is_category ()) {$ mayak_cat_link = get_category_link (get_query_var ( 'cat')); $ Mayak_category_link = mayak_link_paged ($ mayak_cat_link); {Echo "". '<Link rel = "canonical" href = "'. $ Mayak_category_link. '" />'."\n "; }} Else if (function_exists ( 'is_tag') && is_tag ()) {$ tag = get_term_by ( 'slug', get_query_var ( 'tag'), 'post_tag'); if (! empty ($ tag-> term_id)) {$ tag_link = get_tag_link ($ tag-> term_id); } $ Mayak_tag_link = mayak_link_paged ($ tag_link); $ Mayak_tag_link = trailingslashit ($ mayak_tag_link); {Echo "". '<Link rel = "canonical" href = "'. $ Mayak_tag_link. '" />'."\n "; }} Else if (is_author ()) {global $ cache_userdata; $ Userid = get_query_var ( 'author'); $ Mayak_auth_link = get_author_posts_url ( 'ID'); $ Mayak_author_link = mayak_link_paged ($ mayak_auth_link); {Echo "". "<Link rel =" canonical "href =" '. $ Mayak_author_link. "" />'."\n "; }} Else if (is_date ()) {if (get_query_var ( 'm')) {$ m = preg_replace ( '/ [^ 0-9] /', '', get_query_var ( 'm')); switch (strlen ($ m)) {case 0: $ mayak_date_link = get_year_link ($ m); $ Mayak_date_link = mayak_link_paged ($ mayak_date_link); break; case 1: $ mayak_date_link = get_month_link (substr ($ m, 0, 4), substr ($ m, 4, 2)); $ Mayak_date_link = mayak_link_paged ($ mayak_date_link); break; case 2: $ mayak_date_link = get_day_link (substr ($ m, 0, 4), substr ($ m, 4, 2), substr ($ m, 6, 2)); $ Mayak_date_link = mayak_link_paged ($ mayak_date_link); break; default: $ mayak_date_link = ''; }} If (is_day ()) {$ mayak_date_link = get_day_link (get_query_var ( 'year'), get_query_var ( 'monthnum'), get_query_var ( 'day')); $ Mayak_date_link = mayak_link_paged ($ mayak_date_link); } Else if (is_month ()) {$ mayak_date_link = get_month_link (get_query_var ( 'year'), get_query_var ( 'monthnum')); $ Mayak_date_link = mayak_link_paged ($ mayak_date_link); } Else if (is_year ()) {$ mayak_date_link = get_year_link (get_query_var ( 'year')); $ Mayak_date_link = mayak_link_paged ($ mayak_date_link); } {Echo "". '<Link rel = "canonical" href = "'. $ Mayak_date_link." "/>'."\n"; }}} Function mayak_link_paged ($ link) {$ mayak_page = get_query_var ( 'paged'); $ Mayak_check = function_exists ( 'user_trailingslashit'); if ($ mayak_page && $ mayak_page> 1) {$ link = trailingslashit ($ link). "page /". "$ Mayak_page"; if ($ mayak_check) {$ link = user_trailingslashit ($ link, 'paged'); } Else {$ link. = '/'; }} Return $ link; } Add_action ( 'wp_head', 'mayak_canonical'); / *** Кінець функції виведення rel = "canonical" *** /

Тепер ніякі плагіни не зможуть вплинути на коректність виведення атрибута. Можете провести свої тести, на предмет наявності rel = "canonical" на тестованих сторінках і відписатися в коментарях.

доповнення

Якщо потрібно, щоб в навігації canonical завжди вказував на першу сторінку, то треба зробити наступне.

Рядок №87:

$ Link = trailingslashit ($ link). "Page /". "$ Mayak_page";

Змінити на:

$ Link = trailingslashit ($ link);

До зустрічі!

З повагою, Віталій Кирилов

Html?
Про що це говорить?
Чим це загрожує?
А вам цікаво, чому розробники плагіна так прорахувалися з функцією get_permalink ()?
Яку смислове навантаження вони несуть з точки зору SEO?
Php, що перебувати в шаблоні і після тега <?