当前位置: 首页 > 面试题库 >

CORS问题-所请求的资源上没有“ Access-Control-Allow-Origin”标头

拓拔曦
2023-03-14
问题内容

我已经创建了两个Web应用程序-客户端和服务应用程序。
当客户端和服务应用程序部署在同一Tomcat实例中时,它们之间的交互就很好。
但是,当将应用程序部署到单独的Tomcat实例(不同的计算机)中时,请求发送服务应用程序时出现以下错误。

Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource. 
Origin 'http://localhost:8080' is therefore not allowed access. The response had HTTP status code 401

我的客户端应用程序使用JQuery,HTML5和Bootstrap。

如下所示进行AJAX呼叫服务:

var auth = "Basic " + btoa({usname} + ":" + {password});
var service_url = {serviceAppDomainName}/services;

if($("#registrationForm").valid()){
    var formData = JSON.stringify(getFormData(registrationForm));
    $.ajax({
        url: service_url+action,
        dataType: 'json',
        async: false,
        type: 'POST',
        headers:{
            "Authorization":auth
        },
        contentType: 'application/json',
        data: formData,
        success: function(data){
            //success code
        },
        error: function( jqXhr, textStatus, errorThrown ){
            alert( errorThrown );
        });
}

我的服务应用程序使用Spring MVC,Spring Data JPA和Spring Security。

我包含了CorsConfiguration如下所示的类:

CORSConfig.java

@Configuration
@EnableWebMvc
public class CORSConfig extends WebMvcConfigurerAdapter  {
    @Override
    public void addCorsMappings(CorsRegistry registry) {
        registry.addMapping("*");
    }
}

SecurityConfig.java:

@Configuration
@EnableGlobalMethodSecurity(prePostEnabled = true)
@EnableWebSecurity
@ComponentScan(basePackages = "com.services", scopedProxy = ScopedProxyMode.INTERFACES)
public class SecurityConfig extends WebSecurityConfigurerAdapter {

    @Autowired
    @Qualifier("authenticationService")
    private UserDetailsService userDetailsService;

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

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

    @Override
    protected void configure(HttpSecurity http) throws Exception {
       http
                .authorizeRequests()
                .antMatchers("/login").permitAll()
                .anyRequest().fullyAuthenticated();
        http.httpBasic();
        http.sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS);
        http.csrf().disable();
    }

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

    @Bean
    public DaoAuthenticationProvider authenticationProvider() {
        DaoAuthenticationProvider authenticationProvider = new DaoAuthenticationProvider();
        authenticationProvider.setUserDetailsService(userDetailsService);
        authenticationProvider.setPasswordEncoder(passwordEncoder());
        return authenticationProvider;
    }
}

Spring Security依赖项:

 <dependency>
            <groupId>org.springframework.security</groupId>
            <artifactId>spring-security-config</artifactId>
            <version>3.2.3.RELEASE</version>
</dependency>
<dependency>
            <groupId>org.springframework.security</groupId>
            <artifactId>spring-security-web</artifactId>
            <version>3.2.3.RELEASE</version>
</dependency>

我正在使用Apache Tomcat服务器进行部署


问题答案:

CORS的预检请求使用OPTIONS不带凭据的HTTP ,请参阅跨域资源共享:

否则,请发出预检请求。使用方法OPTIONS和以下附加约束,使用引荐来源来源作为覆盖引荐来源,并设置了手动重定向标志和块cookie标志,从起源来源起点获取请求URL:

  • 包括一个Access-Control-Request-Method标头,并将请求方法作为标头字段值(即使是简单方法也是如此)。
  • 如果作者请求标头不为空,则包含一个Access-Control-Request-Headers标头,并以字母顺序将按字母顺序排列的作者请求标头中的标头字段名的列表以逗号分隔,作为标头字段值,每个都转换为ASCII小写(即使是更多是一个简单的标题)。
  • 排除作者请求标头。
  • 排除用户凭据。
  • 排除请求实体主体。

你必须允许HTTP匿名访问OPTIONS。

你修改(简化)的代码

@Override
protected void configure(HttpSecurity http) throws Exception {
   http
       .authorizeRequests()
           .andMatchers(HttpMethod.OPTIONS, "/**").permitAll()
           .antMatchers("/login").permitAll()
           .anyRequest().fullyAuthenticated()
           .and()
       .httpBasic()
           .and()
       .sessionManagement()
           .sessionCreationPolicy(SessionCreationPolicy.STATELESS)
           .and()
       .csrf().disable();
}

从Spring Security 4.2.0开始,你可以使用内置支持,请参阅Spring Security Reference:

  1. CORS

Spring Framework为CORS提供了一流的支持。必须在Spring Security之前处理CORS,因为飞行前请求将不包含任何cookie(即JSESSIONID)。如果请求不包含任何cookie,并且首先使用Spring Security,则该请求将确定用户未通过身份验证(因为请求中没有cookie),并拒绝该用户。

确保首先处理CORS的最简单方法是使用CorsFilter。用户可以CorsFilter通过CorsConfigurationSource使用以下命令将集成到Spring Security中:

@EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {

  @Override
  protected void configure(HttpSecurity http) throws Exception {
      http
          // by default uses a Bean by the name of corsConfigurationSource
          .cors().and()
          ...
  }

  @Bean
  CorsConfigurationSource corsConfigurationSource() {
      CorsConfiguration configuration = new CorsConfiguration();
      configuration.setAllowedOrigins(Arrays.asList("https://example.com"));
      configuration.setAllowedMethods(Arrays.asList("GET","POST"));
      UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
      source.registerCorsConfiguration("/**", configuration);
      return source;
  }
}


 类似资料:
  • 问题内容: 我需要通过JavaScript 将数据发送到Python服务器。因为我使用的是localhost,所以我需要使用CORS。我正在使用Flask框架及其模块。 作为JavaScript,我有这个: 和Python代码: 但是当我执行它时,我收到以下消息: 我该如何解决?我知道我需要使用一些“ Access-Control-Allow-Origin”标头,但我不知道如何在此代码中实现它。顺

  • 问题内容: 我想访问来自同一域但端口号不同的信息,为此,我添加了响应头。 Servlet代码:( 显示在www.example.com:PORT_NUMBER上) jQuery代码:( 显示在www.example.com上) 几次我收到此错误(在控制台中): 该错误通常在执行时首次发生。第二次允许。 我的问题是代码中或代码中缺少什么? 任何建议将不胜感激。 更新1 我变了: 至: 然后我在控制台

  • 问题 我设法从我的应用程序进入keycloak登录页面。使用“我的登录详细信息”登录后,出现错误: -localhost/:1 CORS策略阻止了从源“http://localhost:4200”访问“https://localhost:8080/auth/realms/pwe-realm/protocol/openid-connect/token”的XMLHttpRequest:请求的资源上没有

  • 我已经使用Python EVE框架编写了一个API。当试图从AngularJS应用程序访问API时,它显示了如下所示的错误: 有什么问题吗

  • 我有一个运行在服务器上的API,还有一个连接到它的前端客户端来检索数据。我对跨域问题做了一些研究,并使其工作。然而,我不确定有什么改变。我现在在控制台中收到这个错误: 谢谢你

  • 我在前端使用Angular,在后端使用Java Spring,但是我得到了错误:,而我确信CORS是启用的。这是我的配置文件: 它工作了,我可以毫无问题地完成所有其他请求,但服务中的这个PUT请求给了我一个错误: 这是我的服务器端: