htaccess redirect for Angular routes

2019-01-01 05:53发布

问题:

I have an angular application with several routes, such as:

site.com/
site.com/page
site.com/page/4

Using angular\'s html5 routing mode, these resolve correctly when you click links to them from within the application, but of course are 404 errors when you do a hard refresh. To fix this, I\'ve tried implementing a basic htaccess rewrite.

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

This works for the angular requests, however when I try to load scripts or make ajax calls within my domain, such as:

<script src=\"/app/programs/script.js\"></script>

This script doesn\'t load - it\'s request is redirected and it tries to load the index.html page as the .htaccess thinks it should reroute the request - not knowing that this file does exist and it should load the file instead of redirect.

Is there any way I can have the htaccess redirect the request to index.html (with the view parameters) only if there is not an actual file that it should resolve to?

回答1:

Use a snippet like:

RewriteEngine on
RewriteCond %{REQUEST_FILENAME} -s [OR]
RewriteCond %{REQUEST_FILENAME} -l [OR]
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^.*$ - [NC,L]

RewriteRule ^(.*) /index.html [NC,L]

This will skip to the actual resource if there is one, and to index.html for all AngularJS routes.



回答2:

There is a problem if app requested directive template file, but file is missing. In some case it caused app requested multiple script file in the index.html.

we should send 404 response instead of index.html file if file does not exist. So i add simple regex pattern to identify missing file request.

RewriteEngine On
# If an existing asset or directory is requested go to it as it is
RewriteCond %{DOCUMENT_ROOT}%{REQUEST_URI} -f [OR]
RewriteCond %{DOCUMENT_ROOT}%{REQUEST_URI} -d
RewriteRule ^ - [L]

# If the requested pattern is file and file doesn\'t exist, send 404
RewriteCond %{REQUEST_URI} ^(\\/[a-z_\\-\\s0-9\\.]+)+\\.[a-zA-Z]{2,4}$
RewriteRule ^ - [L,R=404]

# otherwise use history router
RewriteRule ^ /index.html


回答3:

A poor man\'s solution (not using mod_rewrite):

ErrorDocument 404 /index.html


回答4:

In my case i create .htaccess file like below

RewriteEngine on
RewriteCond %{REQUEST_FILENAME} -s [OR]
RewriteCond %{REQUEST_FILENAME} -l [OR]
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^.*$ - [NC,L]

RewriteRule ^(.*) ./index.html [NC,L]

just added . before /index.html and add that file in my domain like https://example.com/subfolder and it\'s works fine



回答5:

Check out this link : https://stackoverflow.com/a/49455101/5899936 Create .htaccess file in root folder and pase this in the .htaccess

 <IfModule mod_rewrite.c>
  RewriteEngine On
  RewriteBase /
  RewriteRule ^index\\.html$ - [L]
  RewriteCond %{REQUEST_FILENAME} !-f
  RewriteCond %{REQUEST_FILENAME} !-d
  RewriteRule . /index.html [L]
</IfModule>


回答6:

I will provide another detailed htaccess file in case you need to :

  • Considerate the baseUrl and default index file
  • Remove the leading slash to manage :params

Here is my htaccess, very close, but more specific :

DirectoryIndex index.html
RewriteEngine on
RewriteBase /subDir
RewriteCond %{REQUEST_FILENAME} -s [OR]
RewriteCond %{REQUEST_FILENAME} -l [OR]
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^.*$ - [NC,L]
RewriteRule ^(.*) index.html [NC,L]