htaccess rule - relative files - apache

It's probably an easy thing to fix however I tried to google this stuff but I'm not sure how to put it in words so I couldn't find anything which would help me.
I have a problem where my very simple .htaccess changes my url as it supposed to but all the resources are trying to get loaded from a wrong place.
My Url:
http://domain.com/index.html?sport=test
My re-written Url:
http://domain.com/test/
.htaccess:
RewriteEngine On
RewriteRule ^([^/]*)/$ /index.html?sport=$1 [L]
now when I type in: http://domain.com/test/ it loads the correct index file however every resource file is trying to get downloaded from test folder...
this is an example resource file location (relative to the index.html):
css/styles.css
js/main.js
but it's looking for them in:
test/css/styles.css
test/js/main.js
Cheers

You've hit the most common problem people face when switching to pretty URL schemes. Solution is also simple, just use absolute path in your css, js, images files rather than a relative one. Which means you have to make sure path of these files start either with http:// or a slash /.
OR you can try adding this in your page's HTML header:
<base href="/" />

Related

.htaccess redirect match to subfolder

I have the present structure now:
www.site.com/reportddmmyyyy
ex:
www.site.com/report01012015
www.site.com/report05012015
and I would like to move all the reports directory into a main directory: reports
www.site.com/reports/reportddmmyyyy
ex:
www.site.com/reports/report01012015
www.site.com/reports/report05012015
Many users have the old format in their bookmarks, so I need htaccess to detect that someone tried to access www.site.com/reportddmmyyyy
and show the content of reports/reportddmmyyyy without changing the browser URL.
Is it possible? I have been Googling for a long time but maybe I am not searching correctly. Could someone please point me in the right way?
RewriteEngine On
RewriteRule ^report([^/]+)/?$ /reports/report$1 [NC,L]
This rule will rewrite
/report01011990
to
/reports/report01011990
without changing the url in your browser.

Using .htaccess to make subdirectory act like subdomain

It's a little difficult for me to ask the question correctly in title, but mainly here's what I'm trying to figure out.
If I use .htaccess on my website and say I'm trying to create a specific path "redirect" so that anything inside that path uses it's non-redirected path for it's relative path. Sorry for the structure of that sentence.
So for example...
I have my website as-
http://www.example.com/
I want to keep things organized so I create a sub-folder/subdirectory to keep all these folders inside of.
http://www.example.com/projects/
So the folder projects will be the place holder for all future projects and I want to create a folder inside projects for each project, so that I can define a URL for each one like such...
http://www.example.com/SuperFish/
http://www.example.com/AquaFear/
Now the folder for SuperFish and AquaFear would be under http://www.example.com/projects/ but also in their own folder say...
http://www.example.com/projects/01/
http://www.example.com/projects/02/
Now it'd be fine and dandy to keep the links like such, but for memory purposes and to share with other people the links to those projects, I'd like to just create a nice simpler URL with a custom "name". like http://www.example.com/SuperFish/ instead of http://www.example.com/projects/01/.
Now I was able to do this partially with my .htaccess file in the root folder with this code...
RewriteEngine On
Options +FollowSymLinks
RewriteRule ^SuperFish/?$ projects/01/ [NC,L]
RewriteRule ^AquaFear/?$ projects/02/ [NC,L]
The issue with this though is that now I can't use relative paths with my SuperFish or AquaFear made up URL links. Anything such as .css, .js, .etc... Isn't within scope because it's trying to look for those files through the made up URL rather than the real physical one.
So the question is, how would I make it so that I can use my made up URL and also have the webpage load things to the real physical path or somehow fix the relative paths by doing this within the .htaccess file?
The reason I titled this the way it is, is due to subdomains being able to find their files with relative paths even though they're a subdirectory just the same.
Using final $ blocks files inside this two folders from being redirect correctly. You could tried instead :
RewriteEngine On
Options +FollowSymLinks
RewriteRule ^SuperFish/?(.*)$ projects/01/$1 [NC,L]
RewriteRule ^AquaFear/?(.*)$ projects/02/$1 [NC,L]

htaccess different behaviour with trailing slash on the URL

I have the following rules in .htaccess file placed at the root folder
RewriteEngine on
RewriteRule ^/?$ /testsite/index.php?rel=m
RewriteRule ^about/?$ /testsite/aboutus.php?rel=b
RewriteRule ^ict/?$ /testsite/ict.php?rel=b
RewriteRule ^eeap/?$ /testsite/eeap.php?rel=b
The rule for index works fine with or without a trailing slash. However when I hit http://mydomain.com/testsite/about/ the page is served without CSS and images and works fine if the last slash is removed. This happens with the rule for ict too.
For the next rule (eeap) things behave the other way. CSS and images go missing if I end the URL with a slash.
What am I doing wrong here?
You need to think about this from the point of view of the web browser.
If the URL does not end with a slash, "/about" for example, then the web browser assumes that it is looking at a file called "about" in the top-level directory of the web server. So any requests in the page generated by "/about" which have relative paths will cause the web browser to produce a full path based on starting off in the top-level directory. For example, a CSS file path of "css/style.css" will cause the browser to start from the top-level and ask for the file from "/css/style.css".
But if the URL does end with a slash, "/about/" in our example, then the web browser believes that it is looking at a sub-directory called "about". Now that same CSS file path "css/style.css" will cause the web browser to ask for the file from "/about/css/style.css".
One CSS file path will be correct, the other will not. Hence the behaviour you're seeing.
There are a few ways to avoid this. You can tell Apache to permanently redirect all requests to either the URL which ends with a slash, or the URL which does not, so that all visitors will end up looking at the same URL. This makes it possible to know what relative CSS and image paths to use in your web pages.
Or you can modify your web pages so that all file paths for CSS, image, JavaScript, etc, are anchored to the top-level directory. So "css/style.css" would become "/css/style.css" for example (note the forward-slash at the start of the path to tell the browser to start from the top-level directory).
Or you could add a bunch of convoluted mod_rewrite rules to try to catch all possible outcomes for CSS files and the like. I don't favour this approach because it will usually make your ruleset more fragile and complicated.

Htaccess rewrite rules subfolder

i'm quite new in the world of Url Rewriting. I have to do so into our own CMS to have a good looking url and to get a better structure that gives results with search engine (SEO).
This is the background file that do all the job that we now hide with nice URL's:
http://something.com/fr/index.php
This is an example of my structure pattern :
http://something.com/fr/accueil or ...
http://something.com/fr/produits/solives-de-rive-rimboard
The CMS simply create an HTACCESS file into the FR directory for quite basic rewriterule like the following :
Options +FollowSymlinks
RewriteEngine On
RewriteRule produits/solives-de-rive-rimboard index.php?p=144
RewriteRule produits/decoupe-sur-mesure index.php?p=145
RewriteRule produits/panneaux-osb index.php?p=146
RewriteRule produits/boites-de-bois-crates index.php?p=147
RewriteRule produits/palettes-de-bois index.php?p=148
RewriteRule accueil index.php?p=4
RewriteRule a-propos-de-cimdat index.php?p=139
RewriteRule produits index.php?p=140
RewriteRule videos index.php?p=141
RewriteRule nous-joindre index.php?p=142
All works fine for first level page like "accueil", "nous-joindre"...
but I haven't found the work around for page of second and third level like "produits/solives-de-rive-rimboard". The index.php just load fine except that all relative link to this page are a subfolder away (the css, the image, jquery...).
Is there any tag that I can use into the htaccess file to specify that no matter in which level "accueil", "produits/something", or a third level one like "produits/group/something" for the index.php have a basic path ?
I'll prefer looking a work around within the htaccess instead of giving index.php a "<base href="something">" that might give us other problems in our structure.
Thanks
This is an HTML issue, rather than a server or .htaccess problem. If your browser sees something like /category/product it is going to act as if it is in the /category/ folder regardless of where the internal server side redirects are sending the request.
The fix to this is simple, change all of the linking in your html to be relative to the site root. So if you have an image tag like
<img src="img/button.gif" />
change it to
<img src="/img/button.gif" />
This tells the browser the exact path from the root to request files from regardless of your rewrite rules. This needs to be done for all of your relative links, including css and javascripts. It may be a bit of work to do, but once it is done it should make future maintenance much easier since you won't have to worry about the apparent path to the page.
Yes, this could be done via .htaccess fairly simply, but there are side effects, including the fact that search engines could see it as duplicate content and it could increase your server bandwidth use as users can't cache static content efficiently. Your best bet is to follow the best practice now while the site is new and growing than try to fix it later after a workaround has caused problems.

How to use apache's mod_rewrite rewriterule without changing relative paths

I've the following rewrite rule in .htaccess:
RewriteRule ^groups/([^/\.]+)/?$ groupdetail.php?gname=$1 [L,NC]
This takes something like www.example.com/groups/groupname and calls www.example/groupdetail.php?gname=groupname. And it works just fine.
But all the relative links on groupdetail.php use groups/ as the relative path, and I don't want them to. How do I avoid this?
For example, when a user clicks on a link <a href="link.php"> on groupdetail.php?gname=groupname, he's taken to www.example/groups/link.php. I want to take the user to www.example.com/link.php.
Obviously, I want to URL to the user to look like "www.example.com/groups/groupname" so I don't want to use [R]/redirect.
If like me you had hundreds of relative links in the page, insert a <base href=""> in the <head> with an absolute path (could use relative too). You'll need to also make the path to .js files in the <head> absolute because IE and firefox deal with the base href differently. I agree it is an annoying issue.
Relative links are resolved by the browser, not the server, so there is nothing you can do with mod_rewrite.
Either use relative links the go up the hierarchy (../link.php) or use absolute links.
If you do not want to have absolute links or use <base> because you are going to move the page around, you can have the base be generated by php, as following:
echo '<base href="http://'.$_SERVER['SERVER_NAME'].str_replace("index.php","",$_SERVER['PHP_SELF']).'" />';
If you change the rewite rule to do a force redirect (add the [R] option), then the browser will be using the /groupdetail.php URL and the relative links will work fine. However, that adds one redirect and makes the URLs less pretty.
RewriteRule ^groups/([^/.]+)/?$ groupdetail.php?gname=$1 [L,NC,R]
You can use the BASE tag, if you don't want to use absolute paths:
http://www.w3schools.com/tags/tag_base.asp
Hop's answer is correct. The browser sees www.example.com/groups/groupname as the address, so considers that /groups is the current directory. So, any links like <a href=link.php> are assumed to be in the /groups folder.
When the user moves his mouse over the link, he'll see www.example.com/groups/link.php as the link address.
The solution is to use absolute links -- just add a slash before the href:
<a href=/link.php>
The user will then see www.example.com/link.php as the url.
That said, it seems from your question that you are using relative links on purpose... do you have a reason not to use absolute links?