【问题标题】:How to solve error 401 with authorization request如何通过授权请求解决错误 401
【发布时间】:2019-08-23 22:07:01
【问题描述】:

我正在使用 Angular 7 和 Spring Boot 开发应用程序。 我的问题是授权请求。

我已经搜索了很多,我找到的所有解决方案都与我的代码中的相同,但问题是 requests 在 Postman 中运行良好,但不适用于 Angular。

这是错误

这是我的个人资料服务:

getEmployeeById(id: number) {

const httpOptions = {
  headers: new HttpHeaders({
    'Content-Type':  'application/json',
    'Authorization': 'Basic ' + btoa('user:userPass'),
    'Access-Control-Allow-Origin': '*',
    'Access-Control-Allow-Methods': 'GET, POST, PATCH, PUT, DELETE, OPTIONS',
    'Access-Control-Allow-Headers': 'Origin, Content-Type, X-Auth-Token'
  })
};
return this.http.get<UserProfile>( this.baseUrl.oneEmployee.replace(':id', id),
  httpOptions) ;
}

这是 Spring boot 中的安全配置:

@Override
protected void configure(final AuthenticationManagerBuilder auth) throws Exception {
    auth.inMemoryAuthentication()
            .withUser("admin").password(encoder().encode("adminPass")).roles("ADMIN")
            .and()
            .withUser("user").password(encoder().encode("userPass")).roles("USER");
}

@Bean
public PasswordEncoder encoder() {
    return new BCryptPasswordEncoder();
}


@Override
protected void configure(HttpSecurity http) throws Exception {
    /*http
            .csrf().disable()
            .authorizeRequests().anyRequest().authenticated()
            .and()
            .httpBasic();*/

    //http.addFilterBefore(new CorsFilter(), ChannelProcessingFilter.class);
    http.authorizeRequests().antMatchers("/").permitAll()
            .anyRequest().fullyAuthenticated().and().httpBasic().and().csrf().disable();
}

【问题讨论】:

  • CORS 被抛出,因为您请求另一个 url。我不使用弹簧,但(通常)您需要配置请求标头。您可以使用本指南stackoverflow.com/questions/51640206/angular-client-enable-cors
  • 不,问题是我的请求适用于 PostMan,但是当我想使用 Angular 7 运行它时,它传递了正确的标头,但不想授权请求

标签: angular spring-boot spring-security


【解决方案1】:

您在两个不同的端口上使用了两个不同的服务器,因此会引发此错误。 您可以在您的休息控制器上添加@CrossOrigin 或创建一个像这样的拦截器来修复它:

public class CrossOriginInterceptor extends HandlerInterceptorAdapter {

    public static final String REQUEST_ORIGIN_NAME = "Origin";

    public static final String CREDENTIALS_NAME = "Access-Control-Allow-Credentials";
    public static final String ORIGIN_NAME = "Access-Control-Allow-Origin";
    public static final String METHODS_NAME = "Access-Control-Allow-Methods";
    public static final String HEADERS_NAME = "Access-Control-Allow-Headers";
    public static final String MAX_AGE_NAME = "Access-Control-Max-Age";

    private List<String> origins=null;

    @Value("${origin.address}") private String origin;
    @Value("${origin.controlEnabled}") private boolean controlEnabled;

    @PostConstruct
    public void method() {
        List<String> stringList = new ArrayList<String>();
        stringList.add(origin);
        this.origins = stringList;
    }

    @Override 
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {

        if(!controlEnabled){ return super.preHandle(request, response, handler);}

        response.setHeader(CREDENTIALS_NAME, "true");
        response.setHeader(METHODS_NAME, "GET, OPTIONS, POST, PUT, DELETE, PATCH");
        response.setHeader(HEADERS_NAME, "Origin, X-Requested-With, Content-Type, Accept");
        response.setHeader(MAX_AGE_NAME, "3600");

        String reqOrigin = request.getHeader(REQUEST_ORIGIN_NAME);
        if (StringUtils.isEmpty(reqOrigin) || origins.contains(reqOrigin)) {
            response.setHeader(ORIGIN_NAME, reqOrigin);
            return true; // Proceed
        } else {
            response.setHeader(ORIGIN_NAME, origins.iterator().next());
            return false; 
        }
    }
}

并在您的 Spring Config 中添加这些行:

<mvc:interceptors>
<bean id="crossOriginInterceptor"
    class="com.systemevolution.controller.CrossOriginInterceptor" /></mvc:interceptors>

【讨论】:

    猜你喜欢
    • 2020-01-24
    • 2020-09-17
    • 1970-01-01
    • 2016-06-05
    • 1970-01-01
    • 1970-01-01
    • 2022-10-15
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多