Canonical Tagging Plugin for SEO
Dependency :
compile ":canonical:0.1"
Summary
Installation
grails install-plugin canonical
Description
For Search Engine Optimization, it's preferable to align on a single
URL for a given page, rather than enabling multiple URLs to resolve to the
same content. Under Grails, it's very common to have multiple equivalent URLs.
One way to avoid negative impacts due to 'duplicate content' is to
add 'canonical' link tags to each page. See the Google Blog for more details:
http://googlewebmastercentral.blogspot.com/2009/02/specify-your-canonical.htmlThis will map the current controller, action and paramters back to a
'canonical' URL, taking UrlMappings into consideration. For requests without
a controller and action, the actual request URI is assumed to be the desired
canonical (this can be disabled). It orders the query parameters,
so that pages with the same parameters displayed in a different order display the same tag.
It also uses the absolute URL, to address differences that may arise when two different
domain names resolve to the same application pages.This is all that may be required, but the plugin enables some other refinements.CAUTION: This plugin generates absolute URLs for the canonical tags.
Confirm that your grails.serverURL is set properly, such that
absolute URLs are being properly constructed.If turned off, the direct URI set method can still be used to apply canoncial URLs
to requests of this type.
Note that this is a true override:
no query string building, parameter exclusions or URL escaping is applied: the URI is used
exactly as provided.The following URIs:
would resolve to:
Due to parameter ordering, the following URIs:
would both resolve to:
Given a mapping like:
The following URIs:
would all resolve to:
For an exclusion list containing 'session' and 'source',
the following URIs:
would both resolve to:
Note that if you are externally rewriting URLs outside of UrlMappings,
using a tool such as mod_rewrite, this plugin may not produce the desired result:
the plugin is unaware of those rewrites.
Show Canonical
This plugin makes it easy to add 'canonical' link tags to each page in a Grails application. After installing the plugin, the following tag can be added to the <head> section of a layout (or wherever head metadata is managed):<head> … <canonical:show /> … </head>
Exclude Params
In some cases, query parameters are material to the page content, such as an ID parameter. In other cases, the qeury parameter may be required for operations, but is not material to the page content and should be 'ignored' by search engines. In the latter case, these parameters can be excluded from the 'canonical' URLs. The exclusion statement can be applied to all requests by, for example, including it in a global layout. Or, it can be called in a controller or template to apply to a smaller set of requests. To exclude parameters use the following in a layout or template:<canonical:exclude params="['session', 'source']" />View Mappings
For view mappings, there is no controller and action involved. Therefore=, reverse resolution of the 'canonical' URL is not possible. In these cases, the URI can be set directly (see below), the URL can be resolved based on the current request (see below), or, a parameter can be added to the mapping which will be used as the base URI. The query String is rebuilt (and properly escaped) from the request, and parameter exclusions are applied. For a mapping in URLMappings.groovy, the feature can be used in this fashion:"/index"(view:"/index", canonical:"/")
Resolve from Request
If there is no action/controller pair, and no canonical paramter set from URLMappings.groovy, the plugin will try to determine the path using the current request. The path will be built from the HttpServletRequest, the parameters will be built from the current parameter list, and exlcusions applied. The query parameters are then URL-escaped and attached to the pathThis 'best guess' may work well in some systems, and abysmally in others. It can be fully disabled by setting:plugins.canonical.disableResolveFromRequest = trueSet URI
Finally, in some cases it may be preferable to override automatuc resolution of the canonical URL with a specific URI. In this case, use the following in the page template (or the equivalent from a controller):<canonical:set uri="/some/other/place" />Examples
Here are some examples of typically equivalent URLs, and how they map to a single canonical URL:Given a controller called 'example' and an action called 'simple', and the common mappping:"/$controller/$action?/$id?"{
constraints {
// apply constraints here
}
}/example/simple /example/simple/ /example/simple.html /example?action=simple
<link rel="canonical" href="http://www.domain.com/example/simple"/>
/example/simple?a=1&z=2 /example/simple?z=2&a=1
<link rel="canonical" href="http://www.domain.com/example/simple?a=1&z=2"/>
"/someMapping/$id"{
controller: 'example', action: 'mapped'
}/example/mapped?id=extra /example/mapped/extra /someMapping/extra
<link rel="canonical" href="http://www.domain.com/someMapping/extra"/>
/example/simple?a=1&source=fb&z=2 /example/simple?z=2&session=12345&a=1&source=fb
<link rel="canonical" href="http://www.domain.com/example/simple?a=1&z=2"/>