代码之家  ›  专栏  ›  技术社区  ›  N Sharma

刷新页面会导致404错误-角度6

  •  12
  • N Sharma  · 技术社区  · 8 年前

    我正在帮助建立一个应用程序 小精灵 以及面临的路由问题。所有的 路线 当我点击一个特定的标签时,但是每当我 刷新 当前页,正在抛出 四百零四 错误。我已经看到很多关于堆栈溢出的文章,但是都没能解决这个问题。

    下面是我的app.module.ts

    import {BrowserModule} from '@angular/platform-browser';
    import {NgModule} from '@angular/core';
    import {RouterModule, Routes} from '@angular/router';
    import {AppComponent} from './app.component';
    import {FetchApiComponent} from './fetch-api/fetch-api.component';
    import {FormsModule} from '@angular/forms';
    import {HttpClientModule} from '@angular/common/http';
    import {UserServiceLatest} from './fetch-latest/app.service';
    import {UserServiceTop} from './fetch-top/app.service';
    import {YoutubePlayerModule} from 'ngx-youtube-player';
    import {SidebarComponent} from './sidebar/sidebar.component';
    import {FetchLatestComponent} from './fetch-latest/fetch-latest.component';
    import { FetchTopComponent } from './fetch-top/fetch-top.component'
    import {UserService} from './fetch-api/app.service';
    import { ServiceWorkerModule } from '@angular/service-worker';
    import { environment } from '../environments/environment';
    import { AngularFireModule } from 'angularfire2';
    import * as firebase from 'firebase';
    import { firebaseConfig } from './../environments/firebase.config';
    import { AngularFireDatabaseModule } from 'angularfire2/database';
    import {PushService} from './push.service';
    
    const appRoutes: Routes = [
      {
        path: '',
    
      component: FetchApiComponent
      }, 
    {
        path: '/latest',
    
        component: FetchLatestComponent
      },
    {
        path: '/top',
    
        component: FetchTopComponent
      },
    {
    path :'*',
    component: FetchApiComponent 
    }
    
    ];
    
    firebase.initializeApp(firebaseConfig);
    
    @NgModule({
      declarations: [
        AppComponent,
        FetchApiComponent,SidebarComponent, FetchLatestComponent, FetchTopComponent
      ],
      imports: [
        RouterModule.forRoot(appRoutes),
        BrowserModule, YoutubePlayerModule,
        FormsModule,
        AngularFireModule.initializeApp(firebaseConfig),
        AngularFireDatabaseModule,environment.production ?ServiceWorkerModule.register('firebase-messaging-sw.js'):[],ServiceWorkerModule.register('/firebase-messaging-sw.js', { enabled: environment.production }),
        HttpClientModule,environment.production ? ServiceWorkerModule.register('ngsw-worker.js') : [], ServiceWorkerModule.register('/ngsw-worker.js', { enabled: environment.production })
      ],
      providers: [UserService,UserServiceTop,UserServiceLatest,PushService],
    
      bootstrap: [AppComponent]
    })
    export class AppModule {}
    

    你能指给我正确的方向吗?

    5 回复  |  直到 8 年前
        1
  •  22
  •   N Sharma    8 年前

    您将在示例url中看到,一旦您得到404错误,就无法使其工作,但是如果您 在前面包含哈希 角度特定的url /#latest 它会起作用的。

    为什么在刷新时停止工作?你的 webserver正在拦截get 从您的浏览器请求并尝试直接转到目录 /latest ,这是不存在的。它不知道它需要去 /bosv2 ,找到一个角度应用程序,然后将小结束位添加到您的路径中,该路径不是真正的目录,而是角度的路由。在您的本地,它的工作方式与您执行ng服务时一样,webpack webserver已经为此做好了准备,但不是您托管应用程序的主机。

    默认情况下,Angular使用 HTML5风格导航 ,但是使用当前的web服务器设置,您将需要旧的angularjs样式(使用hash)。

    从这里开始,你已经 两种解决方案 :

    1. 更改Web服务器配置
    2. 告诉angular使用hashlocationstrategy(完全有效的解决方案),您可以通过提供 useHash: true 在对象中作为appmodule中routermodule.forroot的第二个参数。

      @ ngMead({) 进口: … routermodule.forroot(路由,{usehash:true})//…//latest/ , …

    我想说的是,走杂烩式有一个 有几个缺点 ,这可能与您的场景无关:

    1. 它不产生干净和搜索引擎优化友好的网址,更容易让用户理解和记住。
    2. 不能利用服务器端呈现。

    希望你觉得这个答案有用:)

        2
  •  13
  •   bharat Debdip    8 年前

    使用.htaccess,您还可以尝试以下方法:

    <IfModule mod_rewrite.c>
        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]
    </IfModule>
    
        3
  •  8
  •   GTX Ghazgkull    8 年前

    要避免使用哈希路由,必须正确编辑Web服务器配置,这是最好的解决方案。你只需要对它进行配置,让它回退到 index.html ,这是安格尔的鞋带。虽然没有通用的配置,但这里有一些:

    阿帕奇

    将重写规则添加到 .htaccess 文件

    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 resource doesn't exist, use index.html
    RewriteRule ^ /index.html
    

    小精灵

    使用 try_files 在你的位置块

    try_files $uri $uri/ /index.html;
    

    伊斯

    将重写规则添加到 web.config

    <system.webServer>
      <rewrite>
        <rules>
          <rule name="Angular Routes" 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="/index.html" />
          </rule>
        </rules>
      </rewrite>
    </system.webServer>
    

    来源: https://angular.io/guide/deployment#server-configuration

        4
  •  4
  •   Nimezzz    7 年前

    应用程序内模块.ts

    import {LocationStrategy, HashLocationStrategy} from '@angular/common';
    

    导入后,将以下行添加到提供程序。

    {provide: LocationStrategy, useClass: HashLocationStrategy}
    

    前任:

    providers: [AuthService, 
                AuthGuard, 
                FlxUiDataTable,
                {provide: LocationStrategy, useClass: HashLocationStrategy}]
    

    这会解决你的问题。读 Documentation 在这里。

        5
  •  1
  •   Karan Khanna    7 年前

    我想你得到404是因为你的请求 http://localhost/route Tomcat服务器上不存在。由于angular 2默认使用html 5路由,而不是在url的末尾使用散列,刷新页面看起来像是对不同资源的请求。

    在tomcat上使用角路由时,需要确保服务器在刷新页面时将应用程序中的所有路由映射到main index.html。解决这个问题有多种方法。不管哪个适合你,你都可以去。

    1)将以下代码放入部署文件夹的web.xml中:

    <error-page>
         <error-code>404</error-code>
         <location>/index.html</location>
    </error-page>
    

    2)您还可以尝试将hashLocationStrategy与路由的URL中的一起使用:

    尝试使用:

    routermodule.forroot(路由,{usehash:true})

    而不是:

    routermodule.forroot(路由)

    使用hashlocationstrategy,您的url将如下所示:

    http://localhost/#/route

    3)tomcat url re write valve:如果找不到资源,则使用服务器级配置重定向到index.html重新编写url。

    3.1)在META-INF文件夹中创建一个context.xml文件,并在其中复制下面的上下文。

    <? xml version='1.0' encoding='utf-8'?>
    <Context>
      <Valve className="org.apache.catalina.valves.rewrite.RewriteValve" />
    </Context>
    

    3.2)在WEB-INF中,创建文件rewrite.config(该文件包含URL重写规则,Tomcat使用该规则重写URL)。在rewrite.config中,复制以下内容:

    重写cond%{servlet_path}!-F

    重写规则^/(.*)$/index.html[l]

        6
  •  0
  •   Renish Gotecha    7 年前

    在我的情况下,我做了以下事情

    方法1:

    在你 应用模块.ts 导入下面的内容

    import { HashLocationStrategy, LocationStrategy } from '@angular/common';
    @NgModule({
      declarations: [...],
      imports: [...],
      providers: [{provide: LocationStrategy, useClass: HashLocationStrategy}],
      bootstrap: [AppComponent]
    })
    

    并与

    ng build--base Href/[项目名称]/

    方法2:

    对于NGNIX,

    nano/etc/nginx/站点可用/默认

    在定位块中添加以下行

    location /[PROJECT_NAME] {
      try_files $uri $uri/ /[PROJECT_NAME]/index.html;
    }
    

    sudo服务nginx重启

    并与

    ng build--base Href/[项目名称]/

    推荐文章