views:

97

answers:

2

We are moving from one site language/CMS (coldfusion/custom) to another (PHP/Drupal) and need to have some of our old pages redirected to new ones. I have access to both the .htaccess and httpd.conf (and apache2.conf) as this is a vps on Linode.

Most of them cannot be done via regular expression (they contain GUIDs in the URL) and we're ok writing static redirects.

Here's an example:

  RewriteRule /show.cfm/FG3f4-30F1G/ http://www.mysite.com/john-smith [R=301]

that's it...I've tried the syntax with the starting caret ^, ending dollar sign, none of it seems to work.

I may have a misunderstanding as to what role the RewriteCond plays -- there are other lines already in the .htaccess.

  RewriteCond %{REQUEST_FILENAME} !-f
  RewriteCond %{REQUEST_FILENAME} !-d
  RewriteCond %{REQUEST_URI} !=/favicon.ico
  RewriteRule ^(.*)$ index.php?q=$1 [L,QSA]

Do I need to re-declare the RewriteCond once the RewriteRule is specified?

Also -- Ideally, to preserve cleanliness in the .htaccess, I would like to use a RewriteMap, where I can specify one text file and just have two tab-delimited columns of "old url | new url"...but I can't get that to work either (if it's even appropriate to use).

Any ideas would be MOST welcome...

A: 

For your first static example you would be better off using the Redirect directive rather than mod_rewrites RedirectRule.

A RewriteCond only applies to the RewriteRule that directly follows it. So in your OP the conds states if the requested URI is not a real file or directoruy and it's not the favicon, then redirect it to index.php

With regards to you attempting it with the carat and it not working, this is likely a paths issue and the exact solution depends on whether the RewriteRule is located in the httpd.conf file or in the .htaccess. As a generally rules patterns you are matching in httpd.conf will be preceeded by a forward slash, wheras ones you are matching against in a .htaccess file will not.

Cags
Thanks for your reply; however, using a Redirect (or RedirectMatch) will append the old string to the new string, thus causing a loopFor example:Redirect permanent /index2.html /index1.htmlbecomes:http://www.mysite.com/index.html?q=index2.html
Varian
If that is happening it has nothing to do with the Redirect directive itself and something else is coming into play. Redirect 301 /foo.php /bar.php will take a request for foo.php and will redirect to (plain old) bar.php
Cags
@Cags - `mod_alias` works after `mod_rewrite`, and though the rewritten URL has not be passed through to `mod_alias`, for unintended reasons the modified query string (as per `RewriteRule ^(.*)$ index.php?q=$1 [L,QSA]`) gets appended to the URL that `Redirect` sends back to the client to change to.
Tim Stone
Ahh, I figured it was something like that, but didn't realise mod_rewrite was always executed first.
Cags
A: 

As Cags pointed out, if you're defining your rules in your .htaccess file, you need to make sure that the paths do not contain a leading slash. Additionally, you likely need to make sure to use the L flag, as well as position the redirect rules above the WordPress rewrite section, since both of these things will likely end up causing a conflict otherwise.

For example:

RewriteRule ^/?show.cfm/FG3f4-30F1G/$ http://www.mysite.com/john-smith [R=301,L]

RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_URI} !=/favicon.ico
RewriteRule ^(.*)$ index.php?q=$1 [L,QSA]

If you want to use a RewriteMap, you'll need to define it in your server or virtual server configuration. Normally this is a problem for most people, but since you've indicated that you're on a VPS, I would assume you have the necessary access. Note that it would also be beneficial, for efficiency reasons, to put all of your mod_rewrite directives there, since the .htaccess has to be parsed for each request (but the server configuration is only processed at startup).

Defining a server map would look like this in httpd.conf (or equivalent):

RewriteMap redirect-map txt:/full/path/to/file/pathmap.txt

You would then modify your rule accordingly:

RewriteRule ^/?(show\.cfm/[A-Za-z0-9-]+/)$ http://www.example.com/${redirect-map:$1} [R=301,L]

...with pathmap.txt looking something like:

# Input                Replacement
show.cfm/FG3f4-30F1G/  john-smith
show.cfm/ABC12-40000/  jane-doe
...
Tim Stone