SEO Strict URLs Enforces the use of strict urls to prevent duplicate content.
Official Repository Release: http://www.modxcms.com/SEO-Strict-URLs-1.0-1337.htmlNew support thread: http://modxcms.com/forums/index.php/topic,12452.0.htmlApoXX, has taken this plugin to a new level and now it seems stable enough for an official release. From my understanding it will become part of the core in a soon to be future release.
Note that the code only works on 0.9.5+
If you find any bugs please let us know.
Current Features:
# 301 Redirect from /index.php?id=8 to /alias.html
# 301 Redirect from /page, /page/ to /page.html
# 301 Redirect from non domain.com url to
www.domain.com url (requires .htaccess edit)
# If you switch Friendly URLs off, it redirects /page.html and /page to /index.php?id=48 - this enforces the options that have been selected.
# 301 Redirect /{site_start}, /{site_start}.html to root folder / (no page in url)
# Menu links pointing to "
www.domain.com/{start_page}" are changed to "
www.domain.com" (Can turn off)
# If a page is marked as a folder in the modx system, it shows as /dir/ and not /dir.html (can turn off)
# 301 Redirect /folder to /folder/ to mimic apache, only happens when file is marked as folder (can be turned off)
# Individual URL and link rewriting. For example, you can set rss feed to default to feed.rss, not feed.rss.html. Also, menu links can link directly to the folder name rather than having to go through an extra level of redirects.
ToDo
# Any suggestions?
Change Log
Version 1.0 (summary of all versions up to 1.0)
--------------
# FIXED: All known bugs as of 02/24/2007
# ADDED: Added ability to enforce alternate url extensions such as .cc or .xml
Version 0.7
--------------
# ADDED: If a page is marked as a folder in the modx system, it shows as /dir/ and not /dir.html (can turn off)
# ADDED: 301 Redirect /folder to /folder/ to mimic apache, only happens when file is marked as folder (can be turned off)
Version 0.6
-------------
# FIXED BUG: When installed in modx is subfolder calling /index.html does infinite redirect
# FIXED BUG: When installed in modx is subfolder any redirect adds an extra folder to a redirect url
Install:
Plugin name: SEO Strict URLs
Description: <strong>1.0.0</strong> Enforces the use of strict urls to prevent dup content
Plugin configuration:&editDocLinks=Edit document links;int;1 &makeFolders=Rewrite containers as folders;int;1 &override=Enable manual overrides;int;0 &overrideTV=Override TV name;string;seoOverride
On Install: Check the
OnWebPageInit &
OnWebPagePrerender boxes in the System Events tab.
For overriding documents, create a new template variabe (TV) named seoOverride (or whatever was defined in the configuration) with the following options:
Input Type: DropDown List Menu
Input Option Values: Disabled==-1||Base Name==0||Append Extension==1||Folder==2
Default Value: -1
NOTE: You must set "Enable manual overrides" in plugin configuration to 1 to enable this TV
// Strict URLs
// version 1.0
// Enforces the use of strict URLs to prevent duplicate content.
// By Jeremy Luebke @ www.xuru.com
// Contributions by Brian Stanback @ www.stanback.net
// On Install: Check the "OnWebPageInit" & "OnWebPagePrerender" boxes in the System Events tab.
// Plugin configuration: &editDocLinks=Edit document links;int;1 &makeFolders=Rewrite containers as folders;int;1 &override=Enable manual overrides;int;0 &overrideTV=Override TV name;string;seoOverride
// For overriding documents, create a new template variabe (TV) named seoOverride with the following options:
// Input Type: DropDown List Menu
// Input Option Values: Disabled==-1||Base Name==0||Append Extension==1||Folder==2
// Default Value: -1
// NOTE: You must set "Enable manual overrides" in plugin configuration to 1 to enable this TV
// # Include the following in your .htaccess file
// # Replace "example.com" & "example\.com" with your domain info
// RewriteCond %{HTTP_HOST} .
// RewriteCond %{HTTP_HOST} !^www\.example\.com [NC]
// RewriteRule (.*) http://www.example.com/$1 [R=301,L]
// Begin plugin code
$e = &$modx->event;
if ($e->name == 'OnWebPageInit')
{
$myProtocol = ($_SERVER['HTTPS'] == 'on') ? 'https' : 'http';
$s = $_SERVER['REQUEST_URI'];
$parts = explode("?", $s);
$documentIdentifier = ($modx->documentIdentifier) ? $modx->documentIdentifier : $modx->config['error_page']; // Set error page document ID if page is not found
$alias = $modx->aliasListing[$documentIdentifier]['alias'];
if ($makeFolders) $isfolder = (count($modx->getChildIds($documentIdentifier, 1)) > 0) ? 1 : 0;
if ($override && $overrideOption = $modx->getTemplateVarOutput($overrideTV, $documentIdentifier))
{
switch ($overrideOption[$overrideTV])
{
case 0:
$isoverride = 1;
break;
case 1:
$isfolder = 0;
break;
case 2:
$makeFolders = 1;
$isfolder = 1;
}
}
if ($isoverride)
{
$strictURL = preg_replace('/[^\/]+$/', $alias, $modx->makeUrl($documentIdentifier));
}
elseif ($isfolder && $makeFolders)
{
$strictURL = preg_replace('/[^\/]+$/', $alias, $modx->makeUrl($documentIdentifier)) . "/";
}
else
{
$strictURL = $modx->makeUrl($documentIdentifier);
}
$myDomain = $myProtocol . "://" . $_SERVER['HTTP_HOST'];
$newURL = $myDomain . $strictURL;
$requestedURL = $myDomain . $parts[0];
if ($documentIdentifier == $modx->config['site_start'])
{
if ($requestedURL != $modx->config['site_url'])
{
// Force redirect of site start
header("HTTP/1.1 301 Moved Permanently");
$qstring = preg_replace("#(^|&)(q|id)=[^&]+#", '', $parts[1]); // Strip conflicting id/q from query string
if ($qstring) header('Location: ' . $modx->config['site_url'] . '?' . $qstring);
else header('Location: ' . $modx->config['site_url']);
exit;
}
}
elseif ($parts[0] != $strictURL)
{
// Force page redirect
header("HTTP/1.1 301 Moved Permanently");
$qstring = preg_replace("#(^|&)(q|id)=[^&]+#", '', $parts[1]); // Strip conflicting id/q from query string
if ($qstring) header('Location: ' . $strictURL . '?' . $qstring);
else header('Location: ' . $strictURL);
exit;
}
}
elseif ($e->name == 'OnWebPagePrerender')
{
if ($editDocLinks)
{
$myDomain = $_SERVER['HTTP_HOST'];
$furlSuffix = $modx->config['friendly_url_suffix'];
$baseUrl = $modx->config['base_url'];
$o = &$modx->documentOutput; // get a reference of the output
// Reduce site start to base url
$overrideAlias = $modx->aliasListing[$modx->config['site_start']]['alias'];
$overridePath = $modx->aliasListing[$modx->config['site_start']]['path'];
$o = preg_replace("#((href|action)=\"|$myDomain)($baseUrl)?($overridePath/)?$overrideAlias$furlSuffix#", '${1}' . $baseUrl, $o);
if ($override)
{
// Replace manual override links
$sql = "SELECT tvc.contentid as id, tvc.value as value FROM " . $modx->getFullTableName('site_tmplvars') . " tv ";
$sql .= "INNER JOIN " . $modx->getFullTableName('site_tmplvar_templates') . " tvtpl ON tvtpl.tmplvarid = tv.id ";
$sql .= "LEFT JOIN " . $modx->getFullTableName('site_tmplvar_contentvalues') . " tvc ON tvc.tmplvarid = tv.id ";
$sql .= "LEFT JOIN " . $modx->getFullTableName('site_content') . " sc ON sc.id = tvc.contentid ";
$sql .= "WHERE sc.published = 1 AND tvtpl.templateid = sc.template AND tv.name = '$overrideTV'";
$results = $modx->dbQuery($sql);
while ($row = $modx->fetchRow($results))
{
$overrideAlias = $modx->aliasListing[$row['id']]['alias'];
$overridePath = $modx->aliasListing[$row['id']]['path'];
switch ($row['value'])
{
case 0:
$o = preg_replace("#((href|action)=\"($baseUrl)?($overridePath)?|$myDomain$baseUrl$overridePath/?)$overrideAlias$furlSuffix#", '${1}' . $overrideAlias, $o);
break;
case 2:
$o = preg_replace("#((href|action)=\"($baseUrl)?($overridePath)?|$myDomain$baseUrl$overridePath/?)$overrideAlias$furlSuffix/?#", '${1}' . rtrim($overrideAlias, '/') . '/', $o);
break;
}
}
}
if ($makeFolders)
{
// Replace container links
foreach ($modx->documentListing as $id)
{
if (count($modx->getChildIds($id, 1)))
{
$overrideAlias = $modx->aliasListing[$id]['alias'];
$overridePath = $modx->aliasListing[$id]['path'];
$o = preg_replace("#((href|action)=\"($baseUrl)?($overridePath)?|$myDomain$baseUrl$overridePath/?)$overrideAlias$furlSuffix/?#", '${1}' . rtrim($overrideAlias, '/') . '/', $o);
}
}
}
}
}