Forum Moderators: phranque

Message Too Old, No Replies

Mod_rewrite - Send Old Page PR to New Page

Is it possible?

         

wfernley

5:08 pm on May 10, 2005 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



Hey,

I did some upgrades to my site by adding a mod_rewrite. So now my pages went from product.php?id=12 to /products/widget/index.html. The problem I have is my old pages have the PR with them where my new pages are considered new and have no PR. Is there a way I can forward the old page PR to the new page?

Right now I guess my redirects would be considered temporary because I did not put in the condition that it was permanent. I tried to with [R=permanent] but it didnt work with my site. I am also not using a .htaccess file but instead using the httpd.conf file of Apache.

Can anyone answer this question for me?

Thanks :)

Wes

jdMorgan

8:55 pm on May 10, 2005 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



Please post an example of your current rewriterule(s).

[added] For an example of how to recover your PR and prevent direct linking to the old dynamic URLs, see this recent thread [webmasterworld.com]. [/added]

Jim

wfernley

1:28 pm on May 11, 2005 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



Thanks for the reply, I checked out your link and I added the [R=301,L] to the end of my rewrites but it gave errors. If I added it to the rewrite that would rewrite all .html file extensions to .php extensions it would give me a 403 error and for some reason look to the path of where my site is located on my linux machine (/websites/mysite/ instead of [mysite.com...] Then on the category and product pages it would show the listing.php?input= instead of doing the rewrite.

This is my code:

<Directory />

Options FollowSymLinks
AllowOverride None
RewriteEngine On
RewriteCond %{REQUEST_fileNAME}!-s

# FORWARD OLD products.php to new products/index.php
RewriteRule /products.php products/index.html

# LOOK FOR A CATEGORY
RewriteRule /products/([0-9A-Za-z]+)/index\.html products/listing.php?input=$1

# LOOK FOR A PRODUCT
RewriteRule /products/([0-9A-Za-z]+)/(.*)/index\.html products/listing.php?input=$2
RewriteRule /products/([0-9A-Za-z]+)/(.*)/wtb\.html products/listing.php?input=$2&wtb_showall
RewriteRule /products/([0-9A-Za-z]+)/(.*)/morepics\.html products/listing.php?input=$2&details=morepics
RewriteRule /products/([0-9A-Za-z]+)/(.*)/enlarged-pic\.html products/listing.php?input=$2&details=enlarged-pic
RewriteRule /products/([0-9A-Za-z]+)/(.*)/additional-pic\.html products/listing.php?input=$2&details=additional-pic
RewriteRule /products/([0-9A-Za-z]+)/(.*)/downloads\.html products/listing.php?input=$2&details=downloads
RewriteRule /products/([0-9A-Za-z]+)/(.*)/related\.html products/listing.php?input=$2&details=related
RewriteRule /products/([0-9A-Za-z]+)/(.*)/accessories\.html products/listing.php?input=$2&details=accessories

# Change ALL *.htm, *.html to *.php
RewriteRule ^(.*)\.html$ $1.php

</Directory>

Thanks again for your help!

jd01

8:32 am on May 16, 2005 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



Hi Wes,

It looks like you have contradicting statements:
AllowOverride None

Allows no overrides, should be: (if necessary)
AllowOverride FileInfo

You may also not need the Options directive... I have had this cause an error in the past when trying to use it.

As far as the <directory />, this may also be over kill, since (I assume) you are using .htaccess and it is valid on a per directory basis... including the / directory is not really necessary, because that is the directory you are already in and you are including the full path to your file(s)... If you were defining a 'deeper' directory to shorten your rules it may apply, but I do not normally use it personally. (I just set the .htaccess in the deeper directory most of the time.)

Then I would recommend:
1. Anchoring your rules with ^ and $
2. Removing the redundant A-Z regex and adding a 'no case' [NC] directive instead.
3. Adding a 'last' [L] directive.
4. Reversing your preceding /'s.

RewriteRule ^products/([0-9a-z]+)/(.*)/index\.html$ /products/listing.php?input=$2 [NC,R=301,L]

For detailed definitions of the changes, try the site:webmasterworld comand at a major SE with the key word you are looking for.

If this does not work... let us know, maybe somebody else has better logic than I do at this time of night. (I'm sure there is some more 'tweeking' for performance, but this should be a start.)

Hope this helps.

Justin

wfernley

2:21 pm on May 16, 2005 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



Hi Justin,

Thanks for the reply. I tried using that line you gave, RewriteRule ^products/([0-9a-z]+)/(.*)/index\.html$ /products/listing.php?input=$2 [NC,R=301,L], but unfortunately it gives the same error. Also, I am not using a .htaccess file, I am doing it right in the httpd.conf file itself and that is why I have to specify the directory. Also, I tried removing the AllowOverride and removing the Options directive. The website still worked but that one RewriteRule still gave the same error. Even when I tried to remove the R=301 it still gave the error.

Could it be because I am not using a .htaccess file and it should be worded different?

Thanks again for your help :)

Wes

jdMorgan

3:15 pm on May 16, 2005 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



The main difference in coding between .htaccess and httpd.conf is that in .htaccess context, the leading slash is stripped from the URL 'seen' by RewriteRule. Actually, to be more specific, the path to the directory where the currently-executing .htaccess resides is removed. So, ULRs tested by RewriteRule in .htaccess are 'location-dependent' and are localized to the current .htaccess file's directory.

So, in your Web-root directory .htaccess file, you'd use:


RewriteRule [b]^p[/b]roducts/([0-9a-z]+)/(.*)/index\.html$ /products/listing.php?input=$2 [NC,L]

Whereas, in httpd.conf, you'd use:

RewriteRule [b]^/p[/b]roducts/([0-9a-z]+)/(.*)/index\.html$ /products/listing.php?input=$2 [NC,L]

The second problem is that there are two main forms of URL-modification that mod_rewrite can do. The first, shown in the two lines of code above, is an internal server rewrite. This only changes the file (or script) associated with the requested URL, and does not involve the client (browser or search engine spider) in any way. It simply tells the server to respond with the content of a specified file (or type of file) when a specified URL (or type of URL) is requested. So, and internal rewrite changes the file used to provide content in response to a client URL request.

The second form is an external redirect. This differs from the rewrite in that it changes the URL requested by the client. It sends a response back to the client that says, "This content has moved, use this new URL to fetch it" and provides the new URL in the response-body. After receiving this server redirect response, a client browser will update its address bar with the new URL provided in the response, and then use this new URL to fetch the originally-requested content. For a 301 redirect, a search engine will update its URL database, and again re-request the content using the new URL. It will also 'assign' the old URLs PR to the new URL -- though this make take some time. Since a 302 redirect is defined as temporary, this last step doesn't apply to 302 redirects.

Redirects differ in syntax from internal rewrites in that you must provide a URL, not a local URL-filepath to be used to redirect the client. On some servers, this can be created automatically from a local URL-path, assuming that UseCanonicalName is on (but that can cause other problems in itself). So, the easiest way to do it is to always specify a canonical redirect URL in the RewriteRule substitution, like this:


RewriteRule ^/products/([0-9a-z]+)/(.*)/index\.html$ [b]http:[i][/i]//www.example.com[/b]/products/listing.php?input=$2 [[b]R=301,[/b]NC,L]

Hopefully, changing the syntax of your rule will improve your results. If not, take a look at your server error log -- it often contains very useful information to aid in diagnosing problems.

Jim

wfernley

3:44 pm on May 16, 2005 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



Thanks for the post jdMorgan.

It still gave me an error though ;)

This is what it says in my error_log:

File does not exist: /websites/mysite/products/category

This would be in the address bar:
[mysite.com...]

jd01

7:10 am on May 17, 2005 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



I'm not exactly sure on this, because I do not fully understand what information you need to make your php file serve correctly, but my guess is it has to do with your variables...

This Rule:
RewriteRule ^/products/([0-9a-z]+)/(.*)/index\.html$ /products/listing.php?input=$2 [NC,L]

Applied to this URL:
http://www.mysite.com/products/category/sku/index.html

Would return the information from this page and query string:
http:www.mysite.com/products/listing.php?input=sku

But would not include the 'category' portion of the original url.

To use the category portion or the 1st variable stored, you would need to add $1 to the right side of your rule in the correct format for the php file to serve the information. (When adding the second variable, you may need to add [QSA] to your directives... [NC,QSA,L])

This is just guess.

A double check on your original rules, makes me want to make sure you have added the [L] directive to each rule, or else you may create a loop, or excessive server load. (If you do not specify 'stop processing' by the [L] directive, Apache will just keep processing and attempting to match/rewrite each rule for every URL requested, when what you really want is to match only one and then move on.)

Hope this helps.

Justin

wfernley

1:58 pm on May 17, 2005 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



Hi Justin,

I don't use the category variable so I don't need to add the $1. The page only requires the sku of the product. Should I still add [QSA]?