Trouble with advanced .htaccess redirect - apache

I'm migrating a custom coded blog over to Wordpress, and have to set up a redirect that will handle all of the blog posts.
I need to redirect from this:
/oldblogdirectory/Old_Blog_Posts_Looked_Like_This.htm
to:
/newblogdirectory/new-blog-posts-look-like-this/
Any ideas on the regex for a redirect like this?

Gumbo's approach is certainly the way to do it. I made two test directories:
oldblogdir/archives/blog_posts_look_like_this.htm
newblogdir/archives/blog-posts-look-like-this
And the following RewriteRules redirect successfully. They are only slightly changed to Gumbo's proposal:
RewriteEngine on
RewriteBase /
RewriteRule ^(oldblogdir/archives/[^_]*)_(.*) $1-$2 [N]
RewriteRule ^oldblogdir/archives/(.*?)\.htm$ newblogdir/archives/$1 [R,NC,L]
Note that the [N] causes the .htaccess file to be re-evaluated until the RegEx no longer matches. Therefore you should put it at the very top of the file.

Try this mod_rewrite rules:
RewriteEngine on
RewriteRule ^(oldblogdirectory/[^_]*)_([^_]*)_(.*) /$1-$2-$3 [N]
RewriteRule ^(oldblogdirectory/[^_]*)_(.*) /$1-$2
RewriteRule ^oldblogdirectory/(.+)\.htm$ /newdirectory/$1/ [L,R=301]
But for the uppercase to lowercase conversion you’ll either need a mapping like the internal tolower function or you use PHP for both.

Related

Apache rewrite Subdirectories URL Internally Redirect to Query String

I want to make apache rewrite all links in the form :
host.com/links/<a>/<b>/<c>
such as :
host.com/links/1/2/3
To the form :
host.com/links/?a=1&b=2&c=3
I understand i need to add .htaccess with rewriting rules to links folder but dont really understand the syntax of the rewriting rules.
can any one help?
According to this link
The URL in the browser would be:
host.com/links/1/2/3
The actual page rendered by the server would be:
host.com/links/?a=1&b=2&c=3
Add to .htaccess this lines:
RewriteEngine On
RewriteRule ^/links/([^/]+)/([^/]+)/([^/]+) /?a=$1&b=$2&c=$3 [PT]
When you want to rewrite more complex URLs, you need to create more
complex regular expressions. Just about any pattern can be expressed
as a regular expression, if you break it down into small chunks. This
regular expression breaks down into just a few component parts, once
you get past staring at the seemingly random characters:
[^/]
The above component is a character class containing a "not slash".
So, if we do ...
[^/]*
that means "zero or more not-slash characters". In other words, we're
looking for everything between the slashes. There are two sets of
these, because we're looking for two blocks of things between slashes.
Armed with that little nugget of information, go look at the regular
expression again and see if it makes a little more sense. As with the
earlier , I used the [PT] flag to indicate that the target URL was not
merely a file to be served, but was something that needed to be
handled. In this case, it's going to be a cgi-script handler. So
Apache passes the resulting URL through to that handler.
The basci syntax of rewriting rule is to be followed like below.
Enable mod_rewrite and .htaccess through httpd.conf and then put this code in your .htaccess under DOCUMENT_ROOT directory
Options +FollowSymLinks -MultiViews
# Turn mod_rewrite on
RewriteEngine On
RewriteBase /
RewriteCond %{HTTP_HOST} ^(demo)\.(.+)$ [NC]
RewriteRule ^(setup)/?$ http://www.%2/%1/$1 [L,R=301,NC]
RewriteCond %{HTTP_HOST} ^(demo)\.(.+)$ [NC]
RewriteRule ^(xyz)/?$ http://www.%2/%1/web/$1 [L,R=301,NC]
RewriteCond %{HTTP_HOST} !^demo\. [NC]
RewriteRule ^(xyz)/?$ /web/$1 [L,R=301,NC]
For more informations about rewrite flags
https://httpd.apache.org/docs/2.4/rewrite/flags.html
https://httpd.apache.org/docs/2.4/rewrite/intro.html

.htaccess redirect according to PHP parameters

I'm trying to build some redirections with my .htaccess file to deal with some old forum url. I want the redirections to be made according to the PHP parameters (the topic ID).
For instance, something like
RewriteEngine On
RedirectPermanent /forum/viewtopic.php?t=123 /page1.html
RedirectPermanent /forum/viewtopic.php?t=345 /page7.html
RedirectPermanent /forum/viewtopic.php?t=89 /page3.html
The old and new URL are not related to each other (no PHP parameter has to be kept or something). I want to decide manually in my .htaccess file what to do for each topic ID.
But I can't manage to do that so easily. I tried many things, but nothing works.
Is this possible ? Any idea ?
Thanks a lot !
Edit : additional question : I want to add a global redirection of all the folder /forum to the root of the site ("/"). I guess I can place it after the others, so if no other rule is trigered, this one will be trigered.
I'm trying some things like
RewriteRule ^forum /? [L,R=301]
But everything I have tried so far redirects me to the "page1.html" (my first rule). Any idea why ? Thanks a lot !
You can't match against the query string using mod_alias's Redirect, RedirectMatch, etc. You need to use mod_rewrite and match against the %{QUERY_STRING} variable:
RewriteEngine On
RewriteCond %{QUERY_STRING} ^t=123$
RewriteRule ^forum/viewtopic\.php$ /page1.html? [L,R=301]
RewriteCond %{QUERY_STRING} ^t=345$
RewriteRule ^forum/viewtopic\.php$ /page7.html? [L,R=301]
RewriteCond %{QUERY_STRING} ^t=89$
RewriteRule ^forum/viewtopic\.php$ /page3.html? [L,R=301]
NOte that RewriteEngine is a mod_rewrite directive, not mod_alias. So it has no affect at all on the RedirectPermanent directives.

Apache htaccess rewrite (Pretty URLs)

I have a sneaking suspicion this is not possible, but figured I would ask regardless.
Is it at all possible to take a URL passed to a server in the form of:
http://domain.com/index.php?Action=Controller/Action&one=1&two=2&three=3
And rewrite it to appear as:
http://domain.com/Controller/Action/1/2/3
I am trying to clean up an borderline ancient project to support "Pretty URLs" and I would really like to make the URLs display a bit nicer. I know I could setup a 301 header redirect to the new URL, but I would prefer to avoid that overhead if at all possible.
Any thoughts?
Thanks!
To get
http://domain.com/index.php?Action=Controller/Action&one=1&two=2&three=3
To appear as
http://domain.com/Controller/Action/1/2/3
You will need to use %{QUERY_STRING} to capture the query string data. Your .htaccess file will look like this:
RewriteEngine On
RewriteCond %{QUERY_STRING} ^Action=Controller/Action&one=(\d+)&two=(\d+)&three=(\d+)
RewriteRule ^.+ /Controller/Action/%1/%2/%3 [R=301,L]
This will set up a permanent redirect to the new page. You can play around and test .htaccess rewrite rules here: htaccess.madewithlove.be
You can use this code in your DOCUMENT_ROOT/.htaccess file:
RewriteEngine On
RewriteBase /
RewriteRule ^([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/?$ index.php?Action=$1/$2&one=$3&two=$4&three=$5 [L,QSA]

Simple mod_rewrite RewriteRule for messy legacy url's

Launching a new website for a new client. Their old site has about 50 products and unfortunately, the old product names do not match up to the new URL pattern
Old URL Examples:
example.com/products.aspx?category=Foo&product=SuperLongNoBreakProductNameIDDescription
example.com/products.aspx?category=Foo&product=ProductNameDescription&var1=1293.123
example.com/products.aspx?category=Bar&product=ProductCategoryProdNameRandomNumbers
(The old URL's are sometimes hitting 150+ characters.)
New URL's:
example.com/products/category/actual-product-name
There's no set, recognizable pattern to go from the old product name to the new one. There is for the category.
I've tried simple mod_alias Redirects, but understand that I need a RewriteRule instead. But I'm having problems. All I need is a 1-to-1 redirect for each of these 50 URL's. I thought I could do something like:
RewriteRule ^/products.aspx?category=Foo&product=ProductName
/products/category/new-product-name/ [R=301,NC]
But that isn't working. I know this should be simple, but I am stuck. Any ideas?
Use the pattern below for the rest of your redirect urls. Note that you escape special characters e.g. ? , . and space by adding a \ in front of them
RewriteEngine on
RewriteBase /
RewriteCond %{THE_REQUEST} ^[A-Z]{3,9}\ /products\.aspx\?category=Foo&product=SuperLongNoBreakProductNameIDDescription [NC]
RewriteRule ^ /products/category/new-product-name/ [R=301,NC]
Have a look at the RewriteMap directive of mod_rewrite.
You can specify in a text file something like:
products.aspx?category=Foo&product=SuperLongNoBreakProductNameIDDescription /products/category/new-product-name
And in your httpd.conf
RewriteMap productmap /path/to/map/file.txt
RewriteRule ^(.*) ${productmap:$1} [R=301,NC]
Tip: If it's a permanent redirect you want, make sure you set an appropriate Cache-Control and Expires header to instruct browsers to cache the 301.
You can try something like this:
RewriteEngine On
RewriteCond %{QUERY_STRING} ^category=Foo&product=ProductName$
RewriteRule ^products\.aspx$ /products/category/new-product-name/? [R=301,L]
Notes:
In per-dir (.htaccess) context, the per-dir prefix is stripped, so you can't start the RewriteRule pattern with ^/.
You have to use RewriteCond to match against the query string.
As stated in another answer, a RewriteMap solution might be suited to this situation, if you have access to httpd.conf / the vhost definition for this site. I'm not sure how that works with query strings though.
For something like this, it might be a better solution to rewrite all of these URLs to a server side script, and use the script to do the HTTP redirect for each URL.

Apache - Rewrite Rule confusion

Redirect 301 /resort.php/FOO/BAR http://www.sitename.com.com/index.php
RewriteRule ^/direct/(.*) /direct/$1 [QSA,L] # access non i18n files directly
RewriteRule ^/([a-z]{2}\/.*) /$1 [QSA,L] #any language subdirectory should be left alone
RewriteRule ^/(.*\/$) /en/$1index.php [QSA,L] #fix for links ending in /
RewriteRule ^/(.*\.php) /en/$1 [QSA,L] #any php file with no language subdirectory redirects to the default language
What's the explanation for why the first Redirect 301 isn't going to the homepage? When I replace it with..
RewriteRule ^/resort.php(.*) http://www.sitename.com/index.php [R=301,L]
It starts working. I'm sure it's because I have a bunch of rules and it goes to one and jumps to the other but I'm kinda lost and maybe a guru could explain this more clearly.
My directory structure is like so:
/en/index.php
/direct/
There is no /index.php in the root, I'm redirecting it to en initially.
The Redirect directive is getting into a bun-fight with mod_rewrite. The latter is quite aggressive, and is probably over-writing the redirect HTTP header set on the response by the Redirect directive.
You've already found the solution - use a RewriteRule to perform the redirect. The [L] flag means "last rule - don't process any more", which is how you prevent the rules from interfering with each other. The plain Redirect directive is just an easy way of achieving the simpler functionality of RewriteRule.
RewriteRule /resort.php/FOO/BAR http://www.sitename.com.com/index.php [R=P, L]
your rules arent jumping around, in fact, the L flag means LAST rule, so when one is triggered, the file stops being read.