angularjs html5mode refresh page get 404

2019-01-14 07:20发布

I've created an app using AngularJS with GAE (Google App Engine – Java).

I want to convert it compatible with SEO.

index.html

  • <meta name="fragment" content="!" />
  • <base href="/">

and the body is loaded dynamically through <div ui-view></div>.

app.js

$locationProvider.html5Mode(true);

The url works fine but when I refresh page I get 404 error.

Do you have any idea, what this causes?

6条回答
老娘就宠你
2楼-- · 2019-01-14 07:42

for me, the fix to the the following line as the first line inside tag of you index (main) page:

<base href="/">

Plus you need to configure IIS rewrite rule as following: (make sure you install iis rewrite extension first)

 <system.webServer>
<rewrite>
  <rules>
    <rule name="AngularJS Routes" stopProcessing="true">
      <match url=".*" />
      <conditions logicalGrouping="MatchAll">
                    <add input="{REQUEST_FILENAME}" matchType="IsFile" negate="true" />
                    <add input="{REQUEST_FILENAME}" matchType="IsDirectory" negate="true" />
                    <add input="{REQUEST_URI}" pattern="(api)" negate="true" />
                    <add input="{REQUEST_URI}" pattern="^/(api)" negate="true" />
      </conditions>
      <action type="Rewrite" url="/" />
    </rule>
  </rules>
</rewrite>
    <caching enabled="false" enableKernelCache="false" />

查看更多
女痞
3楼-- · 2019-01-14 07:47

It's been a while since people were looking for this answer but I needed it today. I've made a working example with GAE, angularJS and ng-Route that has pretty formatted links.

Here is the link to the GitHub example

查看更多
你好瞎i
4楼-- · 2019-01-14 07:48

It should be helpful, official angular doc; https://github.com/angular-ui/ui-router/wiki/Frequently-Asked-Questions#how-to-configure-your-server-to-work-with-html5mode

Still I'll paste the relevent part here but I would advice to look at document.

Apache Rewrites

ServerName my-app

DocumentRoot /path/to/app

<Directory /path/to/app>
    RewriteEngine on

    # Don't rewrite files or directories
    RewriteCond %{REQUEST_FILENAME} -f [OR]
    RewriteCond %{REQUEST_FILENAME} -d
    RewriteRule ^ - [L]

    # Rewrite everything else to index.html to allow html5 state links
    RewriteRule ^ index.html [L]
</Directory>

Nginx Rewrites

server {
server_name my-app;

index index.html;

root /path/to/app;

location / {
    try_files $uri $uri/ /index.html;
}
}

Azure IIS Rewrites

<system.webServer>
 <rewrite>
  <rules> 
    <rule name="Main Rule" stopProcessing="true">
      <match url=".*" />
      <conditions logicalGrouping="MatchAll">
        <add input="{REQUEST_FILENAME}" matchType="IsFile" negate="true" />
        <add input="{REQUEST_FILENAME}" matchType="IsDirectory" negate="true" />
      </conditions>
      <action type="Rewrite" url="/" />
    </rule>
  </rules>
</rewrite>

查看更多
神经病院院长
5楼-- · 2019-01-14 07:50

Try adding below section in your grunt file liverload middleware section.

livereload: {
        options: {
          open: true,
          middleware: function (connect) {
            return [
              connect.static('.tmp'),
              connect().use(
                '/bower_components',
                connect.static('./bower_components')
              ),
              connect().use(
                '/app/styles',
                connect.static('./app/styles')
              ),
              connect().use(
                '/apply',
                connect.static('./app/index.html')
              ),
              connect.static(appConfig.app)
            ];
          }
        }
      }  
   }
查看更多
Anthone
6楼-- · 2019-01-14 07:54

For the Java app running on GAE, you can use

URL rewrite filter

You'll find and XML file named urlrewrite.xml . Put all your routes in this xml, and configure it in a way so when you get a request like:

  • /location/edit/120211

it will be redirected to

  • #/location/edit/120211

and your app will have time to be bootstrapped and fire the routing

查看更多
孤傲高冷的网名
7楼-- · 2019-01-14 07:56

I'm sure you've already solved this, but for anybody else running into this issue:

Basically AngularJS's $locationProvider.html5mode(true) makes use of HTML5's history.pushState(), which artificially changes the user's history and address bar URL without reloading the page. If you create a route (in Angular) for /about, but don't have any matching route on the server, you will run into the issue where reloading the page reveals the fact that it's not there on the server. The simplest solution is to mirror your entry point for your app (/index.html?) for all routes accessible by your app.

See: https://stackoverflow.com/a/16570533/1500501

查看更多
登录 后发表回答