Из-за чего при создании иерархии контекста с помощью Fluent API каждый контекст требует отдельный порт?

Ссылка скопирована
1 ответ

По вводным: когда я создаю иерархию контекста с помощью ServletRegistrationBean, то оба DispatcherServlet работают на одном порту:

@SpringBootApplication(exclude = {PropertyPlaceholderAutoConfiguration.class, DispatcherServletAutoConfiguration.class, WebMvcAutoConfiguration.class, ErrorMvcAutoConfiguration.class}) @ConfigurationPropertiesScan public class SocialAppApplication { public static void main(String[] args) { SpringApplication app = new SpringApplication(SocialAppApplication.class); app.run(args); } @Bean public ServletRegistrationBean<DispatcherServlet> secured() { AnnotationConfigWebApplicationContext context = new AnnotationConfigWebApplicationContext(); context.register(SecuredConfig.class); DispatcherServlet servlet = new DispatcherServlet(); servlet.setApplicationContext(context); ServletRegistrationBean<DispatcherServlet> bean = new ServletRegistrationBean<>(servlet); bean.setName("secured"); bean.addUrlMappings("/secured/*"); bean.setLoadOnStartup(1); return bean; } @Bean public ServletRegistrationBean<DispatcherServlet> unsecured() { AnnotationConfigWebApplicationContext context = new AnnotationConfigWebApplicationContext(); context.register(UnsecuredConfig.class); DispatcherServlet servlet = new DispatcherServlet(); servlet.setApplicationContext(context); ServletRegistrationBean<DispatcherServlet> bean = new ServletRegistrationBean<>(servlet); bean.setName("unsecured"); bean.addUrlMappings("/unsecured/*"); return bean; } }

По вводным: но если создавать иерархию контекста с помощью Fluent API

new SpringApplicationBuilder(SocialAppApplication.class).web(WebApplicationType.NONE) .child(SecuredConfig.class).web(WebApplicationType.SERVLET) .child(UnsecuredConfig.class).web(WebApplicationType.SERVLET) .run(args);

Нужно понять: то для каждого контекста требует свой порт. Почему?

Нужно решить такую задачу?

Опишите проблему, и специалист поможет с настройкой, исправлением ошибки или доработкой сайта. Подберём понятный план работ без лишней переписки.

Заказать помощь
Лучший ответ
1
Мария Код Ответ

В Spring разные DispatcherServlet не требуют разные порты сами по себе. Они могут работать на одном порту, если зарегистрированы в одном embedded servlet container с разными URL mappings. Если при Fluent API или иерархии контекстов каждый контекст “просит порт”, значит вы, скорее всего, создаёте несколько независимых web application context, каждый со своим встроенным Tomcat/Jetty/Netty.

Разница такая:

один SpringApplication + несколько DispatcherServlet
  -&gt; один порт, разные mappings
 
несколько SpringApplication.run(...)
  -&gt; несколько embedded server
  -&gt; каждому нужен свой port

один SpringApplication + несколько DispatcherServlet -&gt; один порт, разные mappings несколько SpringApplication.run(...) -&gt; несколько embedded server -&gt; каждому нужен свой port

Если нужны разные MVC-контексты на одном порту, регистрируйте несколько DispatcherServlet внутри одного приложения:

@Bean
public ServletRegistrationBean&lt;DispatcherServlet&gt; apiServlet(
        WebApplicationContext context) {
    DispatcherServlet servlet = new DispatcherServlet(context);
    ServletRegistrationBean&lt;DispatcherServlet&gt; bean =
        new ServletRegistrationBean&lt;&gt;(servlet, "/api/*");
    bean.setName("apiServlet");
    return bean;
}

@Bean public ServletRegistrationBean&lt;DispatcherServlet&gt; apiServlet( WebApplicationContext context) { DispatcherServlet servlet = new DispatcherServlet(context); ServletRegistrationBean&lt;DispatcherServlet&gt; bean = new ServletRegistrationBean&lt;&gt;(servlet, "/api/*"); bean.setName("apiServlet"); return bean; }

Если вы используете Fluent API и создаёте дочерние контексты, убедитесь, что дочерний контекст не запускает свой web server. Не вызывайте для каждого контекста отдельный SpringApplication как полноценное web-приложение.

Также проверьте свойство:

server.port=8080

server.port=8080

Если оно задано в каждом контексте, это признак, что вы поднимаете несколько серверов, а не несколько servlet mapping.

Итог: один порт возможен, но только при одном embedded server. Несколько DispatcherServlet — да, один порт. Несколько независимых Spring Boot web application context — каждому нужен свой порт. Перенесите регистрацию в один контейнер и разведите их по URL mappings.

Другие ответы (0)

Пока нет других ответов. Будьте первым, кто поможет автору.

Ответить на вопрос

комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *

Вам также может быть интересно