4

I have an angular2 application. All works fine, if I using local webpack dev server.

When I deploy application on the server behind nginx I can navigate using application links. But if I enter URL to browser URL bar I get 404 Not Found error.

Here is an Nginx config for site:

server {
    listen 80;
    server_name mydomain;

    location /api {
        proxy_pass http://mydomain:4000;
    }

    location /token-auth {
        proxy_pass http://mydomain:4000;
    }

    location / {
        root /www;
    }
}

Here is my application details:

<base href="/">

@NgModule({
  imports: [
    RouterModule.forRoot(appRoutes),

export const appRoutes:Routes = [
  { path: 'login', component: LoginComponent },
  { path: 'rss', component: RssComponent, data: { section: 1 }, canActivate: [AuthGuard]  },
  { path: '', redirectTo: '/login', pathMatch: 'full' }
];

@Component({
  selector: 'my-app',
  template: `
<div id="application">  
    <app-navigation-tabs></app-navigation-tabs>   
</div>
<div>
    <router-outlet></router-outlet>
</div>
`,
  styleUrls: ['app.component.css']
})

<ul class="nav nav-tabs">
  <li role="presentation" [ngClass]="{active: currentSection === 3}"><a [routerLink]="['/rss']" (click)="toggleSection(3)">RSS</a></li>

I am not sure it is Nginx configuration error, or it is my application error. How can I fix it ?

ceth
  • 44,198
  • 62
  • 180
  • 289
  • I'm more used to apache, but for every single page app, you need to rewrite every request to index.html maybe [this](https://medium.com/@silviopaganini/html5-push-state-nginx-dd7d12b909b7) will help. – n00dl3 Apr 06 '17 at 11:47

2 Answers2

3

I have solved my problem by adding useHash to my router:

RouterModule.forRoot(appRoutes, { useHash: true }),
ceth
  • 44,198
  • 62
  • 180
  • 289
0

I'm an apache guy (don't blame me, it's not my fault it's my sysadmin's). But for every single page apps that uses the History API, you need to rewrite requests to index.html. I found this googling for nginx pushstate that seems to work with nginx. so I guess if you change to this it should work.

server {
    listen 80;
    server_name mydomain;

    location /api {
        proxy_pass http://mydomain:4000;
    }

    location /token-auth {
        proxy_pass http://mydomain:4000;
    }

    location ~ ^/.+/$ {
        root /www;
        rewrite .* /index.html last;
    }
}

EDIT : this solution does not seem to work but I'm gonna dig a bit and update if I find something. And delete otherwise.

n00dl3
  • 21,213
  • 7
  • 66
  • 76
  • I have tried, but it doesn't help. Still 404 error. – ceth Apr 06 '17 at 12:01
  • well maybe I could help if it was apache, but I'm totally useless with nginx. – n00dl3 Apr 06 '17 at 12:06
  • I have solved my problem by adding `useHash` to my router: http://stackoverflow.com/questions/35284988/angular-2-404-error-occur-when-i-refresh-through-browser – ceth Apr 06 '17 at 12:07
  • that's half a solution, You'd better wait for an nginx rewrite solution. – n00dl3 Apr 06 '17 at 12:07
  • `that's half a solution`, why ? – ceth Apr 06 '17 at 12:08
  • 1
    because `useHash:true` uses the `window.location.hash` method, instead of the `History` API. Setting useHash to `true` does not really solve the problem, it just avoids it. (I know that's kinda slight difference). – n00dl3 Apr 06 '17 at 12:12
  • 1
    I'll star this question and try to do such a thing on the weekend, so I'll get a bit into nginx, if I find something I'll let you know. BTW here is a question about [History vs hash for deep-linking](http://stackoverflow.com/questions/9340121/which-one-is-better-pushstate-or-location-hash). Maybe you'll better understand what I meant by half a solution. – n00dl3 Apr 06 '17 at 12:16
  • Sorry, it was my mistake. I forgot to clean cache. When I open private browser tabs I get default Nginx startup page: `Welcome to nginx!` – ceth Apr 06 '17 at 15:27