user2625111
user2625111

Reputation: 213

angularjs html5mode refresh page get 404

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

I want to convert it compatible with SEO.

index.html

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?

Upvotes: 21

Views: 31118

Answers (6)

code_ada
code_ada

Reputation: 884

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>

Upvotes: 11

Igor Rendulic
Igor Rendulic

Reputation: 1

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

Upvotes: 0

asalhani
asalhani

Reputation: 145

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" />

Upvotes: 1

Ramya Ramachandran
Ramya Ramachandran

Reputation: 1151

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)
            ];
          }
        }
      }  
   }

Upvotes: 1

Gokhan Demirtas
Gokhan Demirtas

Reputation: 59

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

Upvotes: 0

Michael Tang
Michael Tang

Reputation: 4896

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

Upvotes: 20

Related Questions