In case of Dynamic page, There's not much you can do from CMS side.You can use below sample:
using System.Web.UI.HtmlControls;
HtmlLink canonicalLink = new HtmlLink();
canonicalLink.Attributes.Add("rel", "canonical");
string absolutePath = Request.Url.AbsolutePath.ToLower();
//The default.aspx should not be present in the canonical Url.
if (absolutePath.Contains("default.aspx"))
{
absolutePath = absolutePath.Replace("default.aspx", string.Empty);
}
canonicalLink.Attributes.Add("href", (CheckSecureRequest() ? "https://" :
"http://") + Request.Url.Host + absolutePath);
// Add the tag to Page header, ID=Head1
this.Head1.Controls.Add(canonicalLink);
You need to set the value of absolutePath
as per your own requirement.
Also, in case of a static page in CMS, you can achieve something similar as below:
1.) Add the below code in Page's DWT. Use a metadata schema for every page.
Here I was using a schema with field CustomCanonicalURL
where I used to set the URL just in case it has something to be completely different.
<!-- TemplateBeginIf cond="(Page.Metadata.CustomCanonicalURL!='')" -->
<input type="hidden" id="hdnCustomCanonicalUrl"
value="@@Page.Metadata.CustomCanonicalURL@@" runat="server" />
<!-- TemplateEndIf -->
Now read the value of this hidden field again at runtime:
HtmlInputHidden hdnCustomCanonicalUrl = null;
string CustomCanonicalUrl = string.Empty;
ContentPlaceHolder headContentPlaceHolder = (ContentPlaceHolder)this.Page.Master.FindControl("pageContent");
if (headContentPlaceHolder != null)
{
hdnCustomCanonicalUrl = (HtmlInputHidden)headContentPlaceHolder.FindControl("hdnCustomCanonicalUrl");
if (hdnCustomCanonicalUrl != null)
{
if (!string.IsNullOrEmpty(hdnCustomCanonicalUrl.Value))
{
CustomCanonicalUrl = hdnCustomCanonicalUrl.Value;
}
}
}
HtmlLink canonicalLink = new HtmlLink();
canonicalLink.Attributes.Add("rel", "canonical");
if (!string.IsNullOrEmpty(CustomCanonicalUrl))
canonicalLink.Attributes.Add("href", CustomCanonicalUrl);
[ All the above .NET code were placed in the master file with the names for ContentPlaceholder
you can simply guess from above sample. The corresponding Content
controls were simply placed in Page's DWT . ]