Difference between revisions of "Enabling Search Engine Friendly (SEF) URLs on IIS"

From Joomla! Documentation

(Minor optimisation of patterns.)
 
(6 intermediate revisions by 2 users not shown)
Line 3: Line 3:
 
Under IIS6, a third-party add-on must be used. Helicon provides one which directly supports .htaccess rules.
 
Under IIS6, a third-party add-on must be used. Helicon provides one which directly supports .htaccess rules.
  
==IIS 7 URL Rewriting==
+
== IIS7 ==
If you have a server running IIS 7 and PHP, you can take advantage of IIS's own internal URL rewriting by using a web.config file similar to the one listed below.
+
{{:Enabling Search Engine Friendly (SEF) URLs on IIS/IIS7}}
  
You can create the file yourself or use the GUI in the IIS7 Manager. You can import .htaccess rules using the GUI/wizard.
+
== IIS6 ==
 +
{{:Enabling Search Engine Friendly (SEF) URLs on IIS/IIS6}}
  
This functionality depends on the presence of the '''IIS URL Rewrite Module''', which does not come with Windows. It is a free download and a Microsoft product.
+
<noinclude>[[Category:IIS]][[Category:Tips and tricks]][[Category:Search Engine Friendly URLs|IIS]]</noinclude>
 
 
===GUI===
 
If the IIS URL Rewrite module is installed, your website manager will have a tool for "URL Rewrite", visible in the IIS Manager's view of your site's configurable IIS modules. The interface is largely self-explanatory. Regular expressions, wildcards or exact matches are all supported.
 
 
 
===web.config===
 
This has been tested on Joomla 1.5 with IIS 7 on Windows Server 2008 with no problems so far. For more information on converting .htaccess to web.config, check out http://learn.iis.net/page.aspx/557/translate-htaccess-content-to-iis-webconfig/
 
 
 
<source lang="xml">
 
<?xml version="1.0" encoding="UTF-8"?>
 
<configuration>
 
    <system.webServer>
 
        <rewrite>
 
            <rules>
 
                <clear />
 
                <rule name="Common Exploit Blocking" stopProcessing="true">
 
                    <match url="^(.*)$" />
 
                    <conditions logicalGrouping="MatchAny">
 
                        <add input="{QUERY_STRING}" pattern="mosConfig_[a-zA-Z_]{1,21}(=|\%3D)" />
 
                        <add input="{QUERY_STRING}" pattern="base64_encode.*\(.*\)" />
 
                        <add input="{QUERY_STRING}" pattern="(\&lt;|%3C).*script.*(\>|%3E)" />
 
                        <add input="{QUERY_STRING}" pattern="GLOBALS(=|\[|\%[0-9A-Z]{0,2})" />
 
                        <add input="{QUERY_STRING}" pattern="_REQUEST(=|\[|\%[0-9A-Z]{0,2})" />
 
                    </conditions>
 
                    <action type="Redirect" url="index.php" appendQueryString="false" redirectType="SeeOther" />
 
                </rule>
 
                <rule name="Joomla Search Rule" stopProcessing="true">
 
                    <match url="(.*)" ignoreCase="true" />
 
                    <conditions logicalGrouping="MatchAll">
 
                        <add input="{URL}" pattern="^/search.php" ignoreCase="true" />
 
                    </conditions>
 
                    <action type="Rewrite" url="/index.php?option=com_content&amp;view=article&amp;id=4" />
 
                </rule>
 
                <rule name="Joomla Main Rewrite Rule" stopProcessing="true">
 
                    <match url="(.*)" ignoreCase="true" />
 
                    <conditions logicalGrouping="MatchAll">
 
                        <add input="{REQUEST_FILENAME}" matchType="IsFile" negate="true" />
 
                        <add input="{REQUEST_FILENAME}" matchType="IsDirectory" negate="true" />
 
                        <add input="{URL}" pattern="(/|\.php|\.html|\.htm|\.feed|\.pdf|\.raw|/[^.]*)$" />
 
                    </conditions>
 
                    <action type="Rewrite" url="index.php/" />
 
                </rule>
 
            </rules>
 
        </rewrite>
 
        <caching>
 
            <profiles>
 
                <add extension=".php" policy="DisableCache" kernelCachePolicy="DisableCache" />
 
            </profiles>
 
        </caching>
 
    </system.webServer>
 
</configuration>
 
 
 
</source>
 
 
 
 
 
==Helicon ISAPI Rewrite==
 
Helicon ISAPI Rewrite 3 located at http://www.helicontech.com/isapi_rewrite/ now provides near identical mod_rewrite functionality.
 
 
 
IIS 7 has its own rewrite module now, the URL Rewrite which works excellent and doesn't require third party installs. It can be enabled
 
through the Web Platform Installer. In the Joomla config turn on both the SEF and Apache mod_rewrite, next create a rule under IIS URL Rewrite:
 
Pattern field: '''^([^/]+)/?$'''
 
Ignore case '''ON'''
 
Action type: '''Rewrite'''
 
Rewrite URL: '''index.php/'''
 
 
 
 
 
 
 
The default rewrite rules can be used and the following code inserted to the top of the index.php file:
 
 
 
<source lang="php">
 
if (isset($_SERVER['HTTP_X_REWRITE_URL']))
 
{
 
    $_SERVER['REQUEST_URI'] = $_SERVER['HTTP_X_REWRITE_URL'];
 
}
 
</source>
 
 
 
 
 
----
 
 
 
First job is to install ISAPI rewriter of your choice
 
http://www.isapirewrite.com/ or http://cheeso.members.winisp.net/IIRF.aspx
 
 
 
ISAPI ReWrite has a lite version (limited) and IIRF (IonicIsapiRewriter) is freeware always updated and the source is free!
 
 
 
Both are configured via file IsapiRewrite4.ini (you dont need to worry about .htaccess.txt ignore it). (if you are using IIRF IonicIsapiRewriter 2.x see below for a change in filename).
 
 
 
The following entries for ISAPI REWRITE:
 
 
 
<source lang="apache">
 
RewriteLog  D:\temp\iirfLog.out
 
RewriteLogLevel 3
 
 
 
IterationLimit 10
 
 
 
# Joomla/Mambo rewrite rules
 
RewriteRule  ^/$                      /index.php
 
RewriteRule ^/content/blogsection/([^/]+)/([^/]+)/ /index.php?option=com_content&task=blogsection&id=$1&Itemid=$2
 
RewriteRule ^/content/blogcategory/([^/]+)/([^/]+)/ /index.php?option=com_content&task=blogcategory&id=$1&Itemid=$2
 
RewriteRule ^/content/section/([^/]+)/([^/]+)/ /index.php?option=com_content&task=section&id=$1&Itemid=$2
 
RewriteRule ^/component/option,([^/]+)/([^/]+),([^/]+)/([^/]+),([^/]+)/([^/]+),([^/]+) /index.php?option=$1&$2=$3&$4=$5&$6=$7
 
RewriteRule ^/component/option,([^/]+)/([^/]+),([^/]+)/([^/]+),([^/]+) /index.php?option=$1&$2=$3&$4=$5
 
RewriteRule ^/component/option,([^/]+)/([^/]+),([^/]+)/ /index.php?option=$1&$2=$3
 
RewriteRule ^/content/category/([^/]+)/([^/]+)/([^/]+)/ /index.php?option=com_content&task=category&sectionid=$1=&id=$2&Itemid=$3
 
RewriteRule ^/content/view/([^/]+)/([^/]+)/([^/]+)/([^/]+)/ /index.php?option=com_content&task=view&id=$1&Itemid=$2&limit=$3&limitstart=$4
 
RewriteRule ^/content/view/([^/]+)/([^/]+)/ /index.php?option=com_content&task=view&id=$1&Itemid=$2
 
</source>
 
 
 
The following is for IIRF IonicIsapiRewriter 1.x:
 
 
 
<source lang="apache">
 
IterationLimit 10
 
</source>
 
 
 
Remark: If you are using IIRF IonicIsapiRewriter Version 2.x you must have a "global" configuration file in the directory where the DLL is and a site specific file (see Artio JoomSEF below as example) in the Joomla root. The filename for 2.x is no longer IsapiRewrite4.ini but changed to Iirf.ini (!)
 
 
 
Example for IirGlobal.ini:
 
<source lang="apache">
 
RewriteEngine On
 
RewriteFilterPriority MEDIUM
 
StatusUrl /iirfStatus  RemoteOk
 
# Turn NotifyLog off if you can to optimize speed. If you need to log the original URL turn it on.
 
NotifyLog Off
 
</source>
 
 
 
Tested and working with ARTIO JoomSEF:
 
 
 
<source lang="apache">
 
RewriteCond %{HTTP_URL}            (/|\.html?|\.php|/[^.]*)$  [I]
 
RewriteCond %{REQUEST_FILENAME}    !-f
 
RewriteCond %{REQUEST_FILENAME}    !-d
 
RewriteRule (.*)                /index.php                      [U,L]
 
# only use the U of the [U,L] if you have turned "NotifyLog ON" specified in your IirGlobal.ini
 
MaxMatchCount 10
 
 
 
</source>
 
 
 
Tested and working with default Joomla SEO:
 
 
 
<source lang="apache">
 
RewriteRule ^/$                      /index.php
 
RewriteRule ^/content/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/ /index.php?option=com_content&task=$1&id=$2&Itemid=$3&limit=$4&limitstart=$5
 
RewriteRule ^/content/([^/]+)/([^/]+)/([^/]+)/ /index.php?option=com_content&task=$1&id=$2&Itemid=$3
 
RewriteRule ^/component/option,([^/]+)/([^/]+),([^/]+)/([^/]+),([^/]+)/([^/]+),([^/]+) /index.php?option=$1&$2=$3&$4=$5&$6=$7
 
RewriteRule ^/component/option,([^/]+)/([^/]+),([^/]+)/ /index.php?option=$1&$2=$3
 
</source>
 
 
 
Tested and working with sh404SEF:
 
<source lang="apache">
 
RewriteLogLevel 4 #Make it 0 in to turn debugging off
 
RewriteLog c:\IIRfLogfile.log #Write the absolute path of your file here
 
 
 
MaxMatchCount 10
 
 
 
# don't rewrite any request that goes to administrator
 
RewriteRule ^/administrator  -  [L]
 
 
 
RewriteCond %{HTTP_URL} (/|\.html?|\.php|!administrator|/[^.]*)$ 
 
RewriteCond %{REQUEST_FILENAME} !-f
 
RewriteCond %{REQUEST_FILENAME} !-d
 
RewriteRule (.*) /index.php [U,L]
 
</source>
 
 
 
Other Third party SEO should work once to follow there rewrite conditions/rules.
 
I run IonicIsapiRewriter-1.2.12b the betas are rock solid and I use it on my production servers with no issues.
 
Please follow vendors installation instructions to get the ISAPI filter working on your IIS server.
 
 
 
<noinclude>[[Category:IIS]][[Category:Tips and tricks]][[Category:Tips and tricks 1.0]][[Category:Tips and tricks 1.5]]</noinclude>
 

Latest revision as of 10:03, 9 June 2011

Under IIS7, a native URL Rewite module is available. It stores rules in a site's web.config file, expressed in XML format. .htaccess rules can be converted to the web.config format.

Under IIS6, a third-party add-on must be used. Helicon provides one which directly supports .htaccess rules.

IIS7[edit]

<translate> If you have a server running IIS 7 and PHP, you can take advantage of IIS's own internal URL rewriting by using a web.config file similar to the one listed below.</translate>

<translate> You can create the file yourself or use the GUI in the IIS7 Manager. You can import .htaccess rules using the GUI/wizard.</translate>

<translate> This functionality depends on the presence of the IIS URL Rewrite Module, which does not come with Windows. It is a free download and a Microsoft product.</translate>

<translate> ===GUI=== </translate> <translate> If the IIS URL Rewrite module is installed, your website manager will have a tool for URL Rewrite, visible in the IIS Manager's view of your site's configurable IIS modules. The interface is largely self-explanatory. Regular expressions, wildcards or exact matches are all supported.</translate>

<translate> In the Joomla config turn on both the SEF and Apache mod_rewrite. Next create a rule under IIS URL Rewrite:</translate>

Pattern field: ^([^/]+)/?$
Ignore case ON
Action type: Rewrite
Rewrite URL: index.php/

<translate>=== web.config === </translate> <translate> This has been tested on Joomla 1.5 with IIS 7 on Windows Server 2008 with no problems so far. For more information on converting .htaccess to web.config, see Translate .htaccess Content to IIS web.config</translate>

<?xml version="1.0" encoding="UTF-8"?>
<configuration>
    <system.webServer>
        <rewrite>
            <rules>
                <clear />
                <rule name="Common Exploit Blocking" stopProcessing="true">
                    <match url="^(.*)$" />
                    <conditions logicalGrouping="MatchAny">
                        <add input="{QUERY_STRING}" pattern="mosConfig_[a-zA-Z_]{1,21}(=|\%3D)" />
                        <add input="{QUERY_STRING}" pattern="base64_encode.*\(.*\)" />
                        <add input="{QUERY_STRING}" pattern="(\&lt;|%3C).*script.*(\>|%3E)" />
                        <add input="{QUERY_STRING}" pattern="GLOBALS(=|\[|\%[0-9A-Z]{0,2})" />
                        <add input="{QUERY_STRING}" pattern="_REQUEST(=|\[|\%[0-9A-Z]{0,2})" />
                    </conditions>
                    <action type="Redirect" url="index.php" appendQueryString="false" redirectType="SeeOther" />
                </rule>
                <rule name="Joomla Search Rule" stopProcessing="true">
                    <match url="(.*)" ignoreCase="true" />
                    <conditions logicalGrouping="MatchAll">
                        <add input="{URL}" pattern="^/search.php" ignoreCase="true" />
                    </conditions>
                    <action type="Rewrite" url="/index.php?option=com_content&amp;view=article&amp;id=4" />
                </rule>
                <rule name="Joomla Main Rewrite Rule" stopProcessing="true">
                    <match url="(.*)" ignoreCase="true" />
                    <conditions logicalGrouping="MatchAll">
                        <add input="{URL}" pattern="(/[^.]*|\.(php|html?|feed|pdf|raw))$" />
                        <add input="{REQUEST_FILENAME}" matchType="IsFile" negate="true" />
                        <add input="{REQUEST_FILENAME}" matchType="IsDirectory" negate="true" />
                    </conditions>
                    <action type="Rewrite" url="index.php/" />
                </rule>
            </rules>
        </rewrite>
        <caching>
            <profiles>
                <add extension=".php" policy="DisableCache" kernelCachePolicy="DisableCache" />
            </profiles>
        </caching>
    </system.webServer>
</configuration>


IIS6[edit]

Under IIS6, a third-party add-on must be used to enable Search Engine Friendly URLs. Helicon provides one which directly supports .htaccess rules.

Tutorials are available for at least the following versions:

Some of these tutorials are included below.

Joomla! 1.5 Joomla 1.5 and newer[edit]

There are several steps one must take to get Search Engine Friendly (SEF) URLs to work properly when using Joomla! on Microsoft's Internet Information Server (IIS) web servers. The following instructions should result in functional SEF URLs using Joomla! 1.5 and IIS6. The only caveat is that you need access to the server itself to install the ISAPI filter in step 1, so either you should be hosting your own server (not shared) or leasing a dedicated server from your web host. If you're using shared hosting, you will have to convince your web host to install it for you.

1) Install an ISAPI filter onto the web server that mimics mod_rewrite. There are several, some may be free but most are commercial applications. The important thing to remember is that it must mimic Apache's mod_rewrite. For example, Helicon's ISAPI_Rewrite 3 is commercial. There is a free version of the program which is limited in that it only allows a single configuration for all sites hosted on the server. To get individual site or directory configurations, you must pay for the full version.

2) Create a new file at the root of the Joomla! site called .htaccess and place the following in that file:

RewriteEngine On
RewriteCond %{REQUEST_URI} (/[^.]*|\.(html?|php))$  [NC]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule .* /index.php

3) Put the following after the opening <?php tag in Joomla!'s main index.php file:

if (isset($_SERVER['HTTP_X_REWRITE_URL']))
{
    $_SERVER['REQUEST_URI'] = $_SERVER['HTTP_X_REWRITE_URL'];
}

4) Enter a value for $live_site in Joomla!'s configuration.php file:

var $live_site = 'http://www.example.com/site1';

5) In Joomla!'s Global Configuration page, check the boxes next to all three SEF options and save the configuration, OR install a 3rd-party SEF component and enable it ([1] is known to work with this configuration).

At this point you should have a working Joomla! install utilising SEF URL's.

Joomla! 1.0 Joomla 1.0[edit]

First job is to install ISAPI rewriter of your choice http://www.isapirewrite.com/ or http://cheeso.members.winisp.net/IIRF.aspx

ISAPI ReWrite has a lite version (limited) and IIRF (IonicIsapiRewriter) is freeware always updated and the source is free!

Both are configured via file IsapiRewrite4.ini (you dont need to worry about .htaccess.txt ignore it). (if you are using IIRF IonicIsapiRewriter 2.x see below for a change in filename).

The following entries for ISAPI REWRITE:

RewriteLog  D:\temp\iirfLog.out
RewriteLogLevel 3

IterationLimit 10

# Joomla/Mambo rewrite rules
RewriteRule  ^/$                      /index.php [L]
RewriteRule ^/content/blogsection/([^/]+)/([^/]+)/ /index.php?option=com_content&task=blogsection&id=$1&Itemid=$2 [L]
RewriteRule ^/content/blogcategory/([^/]+)/([^/]+)/ /index.php?option=com_content&task=blogcategory&id=$1&Itemid=$2 [L]
RewriteRule ^/content/section/([^/]+)/([^/]+)/ /index.php?option=com_content&task=section&id=$1&Itemid=$2 [L]
RewriteRule  ^/component/option,([^/]+)/([^/]+),([^/]+)/([^/]+),([^/]+)/([^/]+),([^/]+) /index.php?option=$1&$2=$3&$4=$5&$6=$7 [L]
RewriteRule ^/component/option,([^/]+)/([^/]+),([^/]+)/([^/]+),([^/]+) /index.php?option=$1&$2=$3&$4=$5 [L]
RewriteRule ^/component/option,([^/]+)/([^/]+),([^/]+)/ /index.php?option=$1&$2=$3 [L]
RewriteRule ^/content/category/([^/]+)/([^/]+)/([^/]+)/ /index.php?option=com_content&task=category&sectionid=$1=&id=$2&Itemid=$3 [L]
RewriteRule ^/content/view/([^/]+)/([^/]+)/([^/]+)/([^/]+)/ /index.php?option=com_content&task=view&id=$1&Itemid=$2&limit=$3&limitstart=$4 [L]
RewriteRule ^/content/view/([^/]+)/([^/]+)/ /index.php?option=com_content&task=view&id=$1&Itemid=$2 [L]

The following is for IIRF IonicIsapiRewriter 1.x:

IterationLimit 10

Remark: If you are using IIRF IonicIsapiRewriter Version 2.x you must have a "global" configuration file in the directory where the DLL is and a site specific file (see Artio JoomSEF below as example) in the Joomla root. The filename for 2.x is no longer IsapiRewrite4.ini but changed to Iirf.ini (!)

Example for IirGlobal.ini:

RewriteEngine On
RewriteFilterPriority MEDIUM
StatusUrl /iirfStatus  RemoteOK
# Turn NotifyLog off if you can to optimize speed. If you need to log the original URL turn it on.
NotifyLog Off

Tested and working with ARTIO JoomSEF:

RewriteCond %{HTTP_URL}             (/[^.]*|\.(html?|php))$  [I] 
RewriteCond %{REQUEST_FILENAME}     !-f
RewriteCond %{REQUEST_FILENAME}     !-d
RewriteRule (.*)                /index.php                      [U,L]
# only use the U of the [U,L] if you have turned "NotifyLog ON" specified in your IirGlobal.ini
MaxMatchCount 10

Tested and working with default Joomla SEO:

RewriteRule ^/$                      /index.php [L]
RewriteRule ^/content/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/ /index.php?option=com_content&task=$1&id=$2&Itemid=$3&limit=$4&limitstart=$5 [L]
RewriteRule ^/content/([^/]+)/([^/]+)/([^/]+)/ /index.php?option=com_content&task=$1&id=$2&Itemid=$3 [L]
RewriteRule  ^/component/option,([^/]+)/([^/]+),([^/]+)/([^/]+),([^/]+)/([^/]+),([^/]+) /index.php?option=$1&$2=$3&$4=$5&$6=$7 [L]
RewriteRule ^/component/option,([^/]+)/([^/]+),([^/]+)/ /index.php?option=$1&$2=$3 [L]

Tested and working with sh404SEF:

RewriteLogLevel 4 #Make it 0 in to turn debugging off
RewriteLog c:\IIRfLogfile.log #Write the absolute path of your file here 

MaxMatchCount 10

# don't rewrite any request that goes to administrator
RewriteRule ^/administrator   -   [L]

RewriteCond %{HTTP_URL} (/[^.]*|\.(html?|php)|!administrator)$  
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule (.*) /index.php [U,L]

Other Third party SEO should work once to follow there rewrite conditions/rules. I run IonicIsapiRewriter-1.2.12b the betas are rock solid and I use it on my production servers with no issues. Please follow vendors installation instructions to get the ISAPI filter working on your IIS server.