Noob in mod_rewrite here...I'm developing a new site and using mod_rewrite.
The problem is, when I activate my rules in .htaccess, my links to CSS files and images become unreadable.
For example, I had this:
http://www.dico2rue.com/dictionnaire.php?idW=675&word=Resto-basket
That I transformed to this:
http://www.dico2rue.com/dictionnaire/675/Resto-basket
I know it's probably because the browser is looking for the CSS file in the
http://www.dico2rue.com/dictionnaire/675/css/general.css instead of the base directory, but I was hoping there was a way to to leave physical files alone, and only parse other URLs in order to avoid full paths (which apparently slows down downloas speed...?...).
thanks.
This problem doesn't have anything to do with mod_rewrite; you just need to provide a valid URL to your CSS file in the src attribute of your link tag. The relative URL you probably want to use is "/css/general.css". See the relative URL rfc.
On another note, your thinking about mod_rewrite might be a little off. In your example you are actually providing a resource in the /dictionnaire/675/ path of your server. The fact that you are using mod_rewrite to do it instead of some other method makes no difference.
you need to add these lines to check if it's not a file or directory right before the rewrite rules
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
Related
I have looked around and attempted my own research on this topic but to no avail just yet.
I have a dynamic webpage set up to look for a ID from a database to retrieve elements required. This results in of course the web page looking like www.site.com/page?id=1
My desired outcome would be like a title for this page to be called.
Such as say I had a fruit product it and user went to my site and went to the address /fruit it would it would be the content of ?id=1 just as an example.
I have seen this used on many a site but not sure how this is programmed or works. Is this something to do with a htaccess document?
Thanks in advance. Appreciate all the help.
While this has been asked and answered many times, I know many people find it difficult to search for this since there are so many common "noise" words related to it. For that reason, I believe it's worth answering again.
If you're using Apache as your webserver (which I'm assuming you are since you mention .htaccess), what you're looking for to create those "clean URLs" is mod_rewrite, which takes a set of rules and rewrites the URL requested by the browser to another path or script.
You would typically enable this in your Apache config or in .htaccess, and in a simple form (a one-to-one mapping) at it would look something like this (provided mod_rewrite is installed):
RewriteEngine On
RewriteRule ^fruit$ index.php?type=1 [L]
Now obviously that doesn't scale well if you have a bunch of dynamic pages you want to create, so what you can do is tell all pages that aren't a really file or directory to be passed to a file for processing, like so:
RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule .* index.php [L]
In this case we're rewriting any request that doesn't resolve to a real file or directory to index.php, and then using the "last" flag [L] to stop processing other rules. Then in our PHP script, we can access the virtual path (in this case /fruit) by using $_SERVER['PATH_INFO'] and doing whatever conditional logic we want with that. If you don't get anything in that variable, ensure that the AcceptPathInfo On directive is set in your Apache config or .htaccess.
A way to test the basic concept/logic without having any rewrite rules would be to use a URL like https://example.com/index.php/fruit. You'll then see that in index.php $_SERVER['PATH_INFO'] will contain the string /fruit. You can rewrite URLs to files in other directories, chain rewrite rules, redirect the browser to other URLs, or even edit environment variables.
There are many good tutorials around using mod_rewrite for clean URLs, so I won't attempt to cover all the nuances here. Just know that it's a very powerful tool, but it's also pretty easy to break your rules if you aren't very comfortable with regular expressions or get lost in the many rules that are commonly in a configuration.
Note that if this is an existing site, you'll also want to use mod_rewrite or mod_redirect to redirect the old URLs to the new ones so they don't break (and for the benefit of having a single URL for search rankings).
I have a complex problem that I an unable to solve for days now. Maybe some expert with more knowledge of htaccess functionality will be able to help out.
I have two files placed in the root directory - test.php and files_include.php.
The URL that a user would normally see is:
www.example.com/test.php?cs1=A&cs2=B&cs3=C&cs4=D
Since this is a ugly URL I would like to rewrite it to something better like:
www.example.com/search/A-B-C-D.html
Using a rule in .htaccess like this I can easily rewrite the URL:
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^search/([^-]*)-([^-]*)-([^-]*)-([^-]*)\.html$ /test.php?cs1=$1&cs2=$2&cs3=$3&cs4=$4 [L]
In the file test.php I call for the website config files like this:
include('files_include.php');
Now the problem. As soon as I rewrite the URL to a location different from the root one, I get a really strange issue. The page still renders correct in browser but:
Problem 1. I have to replace src="images with src="../images if I want to see the image correct. This can be easily corrected by giving an absolute link, it is the easier part to do.
But the question is why is the relative path changing? Is .htaccess making the browser think we are in search'/ folder? The answer to this question will help me to identify the main issue, which is Problem2.
Problem 2. Sitemaps generators cannot follow the links on the page once the URL is rewritten, as if it appears blank to them, no matter that in browser all looks fine.
Therefore I am guessing that by rewriting the URL to search/A-B-C-D.html I am breaking something with the inclusion of files_include.php.
Basically, I need a general idea of were to look at and the things I should have in mind when rewriting root/test.php to root/search/A-B-C-D.html
Any suggestions?
Your browser is clueless about 'pretty' and 'ugly' urls. It just requests a folder or a file. If you request http://example.com/search/A-B-C-D.html, to the browser you are requesting a page A-B-C-D.html in the /search/ folder. If you have any relative urls on that page, it will request them relative to that /search/ folder. The browser has no clue, and should have no clue, what the internal representation of a request looks like. Heck, at your end of the line it might even be translated to instructions for a colony of hamsters, which will then send correct data through. The browser doesn't need to know how hamsters behave ;-)
The first problem is easily resolved by making your urls absolute. I wouldn't recommend making them relative to the pretty url. An alternate solutions would be to add the <base> tag to the <head> tag of your page. The href property of this tag will be used as a base for any relative links on your page. See mdn for more information. You would then do:
<head>
<base href="/">
</head>
As for your second problem, the include itself is not the problem. include(..) will first try to find the file in the include_path, and otherwise in the script's directory and the working directory. This doesn't change if you create pretty urls. Apache, and php, still know where the actual file is located you are executing. If an include statement fails to load a file it will generate an error too, which is another way you can tell if the include itself is the problem. See the documentation.
But the question is why is the relative path changing? Is .htaccess making the browser think we are in search'/ folder? The answer to this question will help me to identify the main issue, which is Problem2.
It's changing because the browser is loading /search/something-something-sometrhing-something.html instead of /test.php. The first URL has a relative URI base as: /search/ and the second URL has a base of /.
For the second problem, you could try externally redirecting, but not sure if that'll help the sitemap itself, it depends on the generator. Try adding this rule:
RewriteCond %{THE_REQUEST} \ /+test\.php\?cs1=([^&]*)&cs2=([^&]*)&cs3=([^&]*)&cs4=([^&\ ]*)
RewriteRule ^ /search/%1-%2-%3-%4.html [L,R]
Alright, so pretty much I have this on Htaccess
RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^(.*) index2.php?url=$1
And I'm trying to execute in a php file the following
mime_content_type('Doggy.png')
and it returns an error saying path of file not found, which I'm pretty sure it does exist,
trying to find what the error could be I ended thinking it's htaccess.
Can anybody help me solve this?
Thank you in advanced.
No, it's not your .htaccess rules. Those only rewrite HTTP requests into file execution rules. Once your PHP executes, they have no influence anymore whatsoever.
The problem is simply that the file Doggy.png does not exist relative to the file where this command is executed. The file must be in the same directory as index2.php, assuming that's the file that contains the line mime_content_type('Doggy.png'). Otherwise you need to use relative paths like mime_content_type('../Doggy.png') or mime_content_type('img/Doggy.png').
As we've established already, the problem is not in rewrite rules.
What actually matters is not he relative location of the files, but rather location of your image file relative to a working directory.
For example, if your directory structure is:
/
/index.php
/inc/imagelib.php
/inc/Doggy.png
and you're doing manipulation on Doggy from the imagelib.php, but it is actually included from index.php and your working directory is /, then, despite being in the same folder, you'll need to address the file as inc/Doggy.png.
The working directory may change, depending on what your entry point in the program will be (in case of a web application - where was the file that originally got the request), or (in case of command line), where were you in shell when executing the command.
To avoid problems with relative paths, i suggest using absolute paths.
So (assuming the same scenario as in the previous example), in imagelib.php you would need to construct the path to image path like this:
`$absolute_path = dirname(__FILE__)."/Doggy.png"`
I just inherited a website built in PHP. The main page of www.mysite.com has a href to www.mysite.com/index/35.html somewhere in the page. In the site's root directory and its children there is no document 35.html.
The number 35 is actually an id found in a DB which also holds the html contents of the page.
If I load URL: www.mysite.com/index.php?id=35 the same page loads.
How does PHP know how to automatically convert
/index/35.html
to
/index.php?id=35
EDIT
Based on the answers, I have found a .htaccess file containing rewrite instructions that would explain the functionality.
However, IIS doesn't seem to (or is not configured) know how to use this. (probably because this is an Apache feature?)
So this begs the following question: Is there a way to configure IIS to work with this?
it will be done usign URL Rewriting using .htaccess - should be in the webroot.
It may look something like:
RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ index.php [QSA,L]
May have other bits, but what this basically tells apache is to send anything that DOES NOT physically exist to index.php
It doesn't. There is a mod_rewrite rule that rewrites from /index/foo to /index.php?id=foo, either in a .htaccess file somewhere or in the httpd configuration itself.
RewriteEngine On
RewriteRule ^index/([\d]+)\.html /index.php?id=$1 [NC,L]
This is off the top of my head. Any browsers trying to load an address starting with index/ has any number ending in .html will be internally redirected to index.php?id= whatever the number is.
Edit: Just saw that your working on IIS. This probably won't work for you. Sorry.
I think you will be using .htaccess to redirect all requests to index.php. From there You can pass the query string a routing class, which will parse the url and identify the unique ids.
In this case we can say like, your routing class will parse the request /index/35.html to indexController, indexAction, id=35. now you can pass this id to the model to get corresponding page contents
NB : Here I a am assuming you are using mvc pattern. Anyway it can be treated in your own way, with the concept remaining the same. Hope this make sence.
I'm using mod rewrite to redirect all requests targeting non-existent files/directories to index.php?url=*
This is surely the most common thing you do with mod_rewrite yet I have a problem:
Naturally, if the page url is "mydomain.com/blog/view/1", the browser will look for images, stylesheets and relative links in the "virtual" directory "mydomain.com/blog/view/".
Problem 1:
Is using the base tag the best solution? I see that none of the PHP frameworks out there use the base tag, though.
I'm currently having a regex replace all the relative links to point to the right path before output. Is that "okay"?
Problem 2:
It is possible that the server doesn't support mod_rewrite. However, all public files like images, stylesheets and the requests collector index.php are located in the directory /myapp/public. Normally mod_rewrite points all request to /public so it seems as if public was actually the root directory too all users.
However if there is no mod_rewrite, I then have to point the users to /public from the root directory with a header() call. That means, however that all links are broken again because suddenly all images, etc. have to be called via /public/myimage.jpg
Additional info: When there is no mod_rewrite the above request would look like this: mydomain.com/public/index.php/blog/view/1
What would be the best solutions for both problems?
Edit/Additional question:
Is there a way to make /public/ the base dir using plain htaccess code?
Write the app in such a way that it doesn't need mod_rewrite to function (at the cost of having "ugly" urls). Progressively enhance it with mod_rewrite to achieve the desired result. This probably means that you'll need to store some base path config info in your app.
I don't understand these problems at all.
Yes, this is surely the most common thing you do with mod_rewrite, yet with 2 conditions:
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
So, nothing hurt your existing images.
Why not to use just absolute path, e.g. /myapp/public/myimage.jpg, so, no virtual directory will hurt image path?
what about path info? You could use it without mod_rewrite
/index.php/path/to/another/file.jpg
<?php
echo $_SERVER["PATH_INFO"]; // outputs /path/to/another/file.jpg
?>
Anyways, if you want to know if mod_rewrite is supported by your server :
<?php
echo "mod_rewrite : ".(!empty($_SERVER["REDIRECT_URL"])?"supported":"not supported");
?>
Then you ll know if mod_rewrite is the solution or maybe path_info is more well suited for you, you could make support functions that could look for both too.