Настройки Spring Boot CORS: аннотация CrossOrigin работает addCorsMappings не работает - PullRequest
0 голосов
/ 31 марта 2020

У меня есть приложение Spring Boot Rest, в котором мне нужно разрешить запросы CORS.

Запросы используют общий путь <host>:<port>/api/..., и пока у меня есть только два ресурса:

package my.controllers;

@RestController
@RequestMapping(path="/", produces="application/json")
public class DataController {

    @GetMapping("/")
    public ApiResponse<Map<String, Object>> getValues() {
        // ...
    }

    @GetMapping("/sub")
    public ApiResponse<String> getValuesSub() {
        // ...
    }

Вот два примера запросов от клиента Javascript, работающего на http://localhost:3000/:

fetch('http://localhost:2001/api/').then(/* ... */);
fetch('http://localhost:2001/api/sub')).then(/* ... */);

Если я добавлю аннотацию @CrossOrigin(origins = "*") к контроллеру, запросы CORS будут работать нормально; если я заменим его, реализуя WebMvcConfigurer.addCorsMappings(), хотя:

@ComponentScan(basePackages={ "my.controllers" })
@Configuration
public class WebappConfig implements WebMvcConfigurer {

    // ...

    @Override
    public void addCorsMappings(CorsRegistry registry) {
        LogManager.getLogger(getClass()).info("CORS settings");
        registry.addMapping("/api/**").allowedOrigins("*").maxAge(3600);
    }

CORS-запросы завершатся неудачно, и я получу (в Firefox, Chrome отображается похожее сообщение об ошибке):

CORS header 'Access-Control-Allow-Origin' missing

Я вижу запись в журнале, поэтому метод обязательно вызывается.

Я видел другие вопросы, касающиеся Spring Security или Spring Data (я не использую ни одного), поэтому вот мой список зависимостей на случай, если я что-то упустил :

  • spring-boot-starter-web
  • spring-boot-starter-tomcat
  • spring-boot-starter-log4j2
  • spring -boot-configuration-processor
  • commons-lang3
  • commons-beanutils

Как правильно установить настройки CORS для всего приложения, без использования @CrossOrigin аннотации на каждом контроллере?

ОБНОВЛЕНИЕ

Я инициализирую сервлет Rest следующим образом:

@Bean
public ServletRegistrationBean<DispatcherServlet> registerDispatcherServlet(DispatcherServlet servlet) {
    ServletRegistrationBean<DispatcherServlet> registration = new ServletRegistrationBean<>(servlet);

    servlet.setContextConfigLocation("");
    registration.addUrlMappings("/api/*");
    registration.setLoadOnStartup(1);

    return registration;
}

В журналах написано:

Servlet dispatcherServlet mapped to [/api/*]
Servlet dispatcherServlet mapped to [/]
Servlet dispatcherServlet was not registered (possibly already registered?)

Может ли быть, что данные настройки Cors идут к указанному незарегистрированному сервлету?

1 Ответ

0 голосов
/ 31 марта 2020

Я заработал, заменив "/api/**" на "/**" при вызове addMapping() при настройке реестра CORS:

@Override
public void addCorsMappings(CorsRegistry registry) {
    LogManager.getLogger(getClass()).info("CORS things!");
    registry.addMapping("/**").allowedOrigins("*").maxAge(3600);
}

Хотя я озадачен, почему это настройка, которая заставляет это работать, и что я должен сделать, если мне нужно выставить несколько независимых путей Rest, например:

  • http:/host:port/public-api (со всего Inte rnet)
  • http:/host:port/reserved-api (от известных хостов)
  • http:/host:port/admin-api (только тот же хост)
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...