【问题标题】:Whitelabel Error Page with Angular + Springboot带有 Angular + Springboot 的 Whitelabel 错误页面
【发布时间】:2020-09-22 18:48:38
【问题描述】:

每当我尝试在我的 Angular 9 应用程序上加载任何页面(根路由除外)时,我都会收到一个 Whitelabel 错误页面(错误 404),方法是将 URL 放在浏览器上并按 Enter 键或刷新页面。使用页面按钮(Angular 路由器)加载这些页面效果很好。

我尝试了许多来自 stackoverflow 的解决方案来解决这个问题,但都没有奏效。

whitelabel error page

后端主类

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
public class GroupsApplication {

    public static void main(String[] args) {
        SpringApplication.run(WarcraftgroupsApplication.class, args);
    }

}

后端安全配置器

import com.sampaiodias.groups.auth.filters.JwtRequestFilter;
import com.sampaiodias.groups.auth.services.MyUserDetailsService;
import org.springframework.context.annotation.Bean;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.crypto.password.NoOpPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;

@EnableWebSecurity
public class SecurityConfigurer extends WebSecurityConfigurerAdapter {

    private final MyUserDetailsService myUserDetailsService;
    private final JwtRequestFilter jwtRequestFilter;

    public SecurityConfigurer(MyUserDetailsService myUserDetailsService, JwtRequestFilter jwtRequestFilter) {
        this.myUserDetailsService = myUserDetailsService;
        this.jwtRequestFilter = jwtRequestFilter;
    }

    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth.userDetailsService(myUserDetailsService);
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.csrf().disable().authorizeRequests().antMatchers("/auth", "/user", "/refresh", "/end-session").permitAll()
                .and().sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS);
        http.addFilterBefore(jwtRequestFilter, UsernamePasswordAuthenticationFilter.class);
    }

    @Bean
    public PasswordEncoder passwordEncoder() {
        return NoOpPasswordEncoder.getInstance();
    }

    @Bean
    @Override
    public AuthenticationManager authenticationManagerBean() throws Exception {
        return super.authenticationManagerBean();
    }
}

前端应用路由模块

import { GroupsComponent } from './groups/groups/groups.component';
import { RegisterComponent } from './auth/register/register.component';
import { LoginComponent } from './auth/login/login.component';
import { AppComponent } from './app.component';
import { NgModule } from '@angular/core';
import { Routes, RouterModule } from '@angular/router';

const routes: Routes = [
  {
    path: '',
    component: AppComponent,
  },
  {
    path: 'login',
    component: LoginComponent,
  },
  {
    path: 'register',
    component: RegisterComponent,
  },
  {
    path: 'groups',
    component: GroupsComponent,
  },
  { path: '**', redirectTo: '/' },
];

@NgModule({
  imports: [RouterModule.forRoot(routes)],
  exports: [RouterModule],
})
export class AppRoutingModule {}

前端代理

const PROXY_CONFIG = [
  {
    context: ["/", "/user", "/group", "/character"],
    target: "http://localhost:8080",
    secure: false,
  },
];

module.exports = PROXY_CONFIG;

【问题讨论】:

    标签: angular spring spring-boot spring-security


    【解决方案1】:

    您必须为您在路由模块中设置的每条 Angular 路由转发到 index.html,而不仅仅是根路由。请参阅Spring Boot with redirecting with single page angular2 定义单个控制器以将所有请求转发到 index.html。

    否则 Spring 会尝试自己处理 url,但由于它没有您输入的 url 的 @Controller 请求映射(因为您希望 Angular 处理它),它返回 404。

    编辑

    OP 指的是ng serve,而不是已部署的环境。在这种情况下,您必须创建一个重定向到 ng 开发服务器的 ErrorController - http://localhost:4200

    @Controller
    @RequestMapping("${server.error.path:${error.path:/error}}")
    public class AngularRedirectErrorController extends AbstractErrorController {
    
      private final ErrorAttributes errorAttributes;
    
      public AngularRedirectErrorController(ErrorAttributes errorAttributes) {
        super(errorAttributes);
        this.errorAttributes = errorAttributes;
      }
    
      @RequestMapping(produces = MediaType.TEXT_HTML_VALUE)
      public String redirectToAngular(ServletWebRequest request) {
        Map<String, Object> errorAttrs = errorAttributes.getErrorAttributes(request, false);
        String path = (String) errorAttrs.get("path");
        return "redirect:http://localhost:4200" + path;
      }
    
      @RequestMapping(produces = MediaType.APPLICATION_JSON_VALUE)
      @ResponseBody
      public ResponseEntity<Map<String, Object>> error(HttpServletRequest request) {
        HttpStatus status = getStatus(request);
        if (status == HttpStatus.NO_CONTENT) {
            return new ResponseEntity<>(status);
        }
    
        WebRequest webRequest = new ServletWebRequest(request);
        Map<String, Object> body = errorAttributes.getErrorAttributes(webRequest, false);
        return new ResponseEntity<>(body, status);
      }
    
      @Override
      public String getErrorPath() {
        return null;
      }
    
    }
    

    【讨论】:

    • 这对我不起作用,而不是白标签页面,我得到了一个完全白色的页面。如果我理解这背后的原因,当我在使用 ng serve 运行我的 Angular 应用程序时遇到此错误时,为什么要将我的 Angular 应用程序的构建放在 Spring 静态文件夹中?
    • 哦,你在使用 ng serve!由于您没有提到这一点,我以为您指的是已部署的环境。请参阅我的更新答案。
    • 它确实解决了可白标问题,谢谢!是否可以重定向到我尝试访问的页面而不仅仅是根路由?例如,如果我尝试访问localhost:4200/foo,上面的代码会将我重定向到localhost:4200
    • 发布的解决方案实际上也破坏了我的 JWT 身份验证,当 JWT 令牌过期时(而不是返回 403 或 401)给出以下错误: core.js:6272 错误错误:未捕获(承诺): HttpErrorResponse: {"headers":{"normalizedNames":{},"lazyUpdate":null},"status":200,"statusText":"OK","url":"localhost:4200/…@987654325 解析失败@":{"error":{},"text":"\n\n \n \n...
    • 您的代码修复了 JWT 部分,非常感谢!但是,当涉及到重定向时,它不起作用,页面仍然无法加载。它调用 redirectToAngular 方法 20 次(返回正确的 url + 路径),但浏览器显示 ERR_TOO_MANY_REDIRECTS 错误。
    猜你喜欢
    • 2023-03-13
    • 2021-09-19
    • 2019-04-02
    • 2018-07-22
    • 2022-01-25
    • 2020-10-30
    • 2023-04-01
    • 2017-06-03
    • 1970-01-01
    相关资源
    最近更新 更多