How-to solve two canonical links in Drupal 7?

What you can do when your D7 have two canonical links?

When I finish a new project and put it on the air, I check all links looking for some mistakes like a wrong URL, a bad typed character or just a bad link. I don’t know something so bad like a broke link or that sign showing a broke image in an empty space. Is terrible (for me).

In my last project I followed the same how-to: put the website’s URL in the W3C Link Checker, walk to the kitchen to bring a big mug of coffee, sit and wait. After five minutes, surprise: every page had a wrong link. Checking the project looking these links, I can’t see nothing wrong. Just in case, I recheck the pages using another tool (LinkChecker) but the problems persist.

So, I stopped for check the source code of some pages and I found two canonical links in each page: the first was correct but the second with a wrong address where the language prefix was posted two times (that was a multi language project). The first link I know where it came: from the Metatag module, a great module to manage all kind of information to improve SEO in Drupal websites (it’s a really wonderful module). And the second? Who is the father of that crazy thing? To eliminate some suspicious things, I disabled some modules like Global Redirect but the problem persist (and I spend a couple hours with this issue).

Searching the web, I found the secret (ok, no so secret, but…): Drupal 7 automatically make a canonical link for every page and put it in the header. It’s great when you don’t use another module to manage this kind of information. With two canonical links, the search engines could be crazy and, in some way, put my articles in their ranking down. Another bad thing: Drupal don’t use the absolute URL to create the canonical links, just a relative URL (to change it you need to uncomment the base url line in settings.php). So, the final solution was disappear with the Drupal’s canonical links and use just the Metatag option. But, how?

The trick: use the force and take out the canonical links

In Drupal 7 every page use the html.tpl.php file and there’s the $head variable used to print all metatags. So, if I disabled this variable, my problems are gone, right? Wrong! This variable print more than canonical links and it’s not a good idea to remove it (but if you like some kind of punishment, you can write every piece of information inside of your theme). The solution I found at Drupal’s API website: the html_head_alter hook. With it and a small function inside my template.php file I solved the problem. Look it:

function mytheme_html_head_alter(&$head_elements){
    unset($head_elements['drupal_add_html_head_link:canonical:</node/1>;']);
}

The code above solved the problem just for the node 1 but I need for every node (or page). The answer is:

function mytheme_html_head_alter(&$head_elements){
    foreach (preg_grep('/^drupal_add_html_head_link:canonical:</', array_keys($head_elements)) as $key) {
         unset($head_elements[$key]);
    }
}

Just a looping and a regular expression to remove the canonical links for every page and now, I can use the Metatag module like a charm. This approach is valid for any information that Drupal put inside the header like shortlinks, generator, etc (to find which value that you can remove, use a simple print_r($head_elements inside of the function).

If you have the same problem, cut and paste the function above and put it in your template.php file changing “mytheme” for your theme’s name. But don’t forget: install a module to manage the canonical links. Search engines like it so much.

Good luck.

1 comentário em “How-to solve two canonical links in Drupal 7?

  1. Ranjeesh

    Thank You Very Much. Exact Problem with the exact modules in reference. I applied your fix on our site and it worked like a charm.

Comentários encerrados.