Eazy
Eazy

Reputation: 3472

Apache redirect all to index.php except for existing files and folders

I have index.php that reads full path by $_SERVER[‘REQUEST_URI’] variable. My task is when user enter: www.domain/resource/777 redirect to index.php with path /resource/777 and parse $_SERVER[‘REQUEST_URI’] to do some logic. But I have also real files and folders like:

When I try this config:

RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^(.*)$ /index.php [L]

Client could not get all css and etc files. How to write correct rule in Apache to achive this?

Upvotes: 14

Views: 11085

Answers (5)

Matt Raines
Matt Raines

Reputation: 4218

According to the documentation REQUEST_FILENAME only evaluates to the full local filesystem path to the file if the path has already been determined by the server.

In a nutshell this means the condition will work if it is inside an .htaccess file or within a <Directory> section in your httpd.conf but not if it's just inside a <VirtualHost>. In this latter case, you can simply wrap it in a <Directory> tag to get it working.

<VirtualHost *:80>
     # ... some other config ...
    <Directory /path/to/your/site>
        RewriteEngine On
        RewriteCond %{REQUEST_FILENAME} !-d
        RewriteCond %{REQUEST_FILENAME} !-f
        RewriteRule ^(.*)$ /index.php [L]
    </Directory>
</VirtualHost>

Upvotes: 1

SirDarius
SirDarius

Reputation: 42889

If you are using Apache 2.2.16 or later, you can replace rewrite rules entirely with one single directive:

FallbackResource /index.php

See https://httpd.apache.org/docs/2.2/mod/mod_dir.html#fallbackresource

Basically, if a request were to cause an error 404, the fallback resource uri will be used to handle the request instead, correctly populating the $_SERVER[‘REQUEST_URI’] variable.

Upvotes: 30

Eazy
Eazy

Reputation: 3472

For now only this helped to me:

RewriteEngine On
RewriteCond %{REQUEST_URI} !^/src/
RewriteCond %{REQUEST_URI} !^/assets/
RewriteCond %{REQUEST_URI} !^/resource/
RewriteCond %{REQUEST_URI} !^/data.json
RewriteRule ^(.*)$ /index.php [L]

Upvotes: 0

anubhava
anubhava

Reputation: 785098

Your rule is fine. Issue with css/js/image is that you're using relative path to include them.

You can add this just below <head> section of your page's HTML:

<base href="/" />

so that every relative URL is resolved from that base URL and not from the current page's URL.

Also keep just this rule in your .htaccess:

DirectoryIndex index.php
RewriteEngine On

RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^[^.]+$ index.php [L]

Upvotes: 3

mario.van.zadel
mario.van.zadel

Reputation: 2949

You can set the error document in your htaccess file so that index.php will be used then a non existing file is requested:

ErrorDocument 404 /index.php

Upvotes: 0

Related Questions