加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 编程开发 > Java > 正文

java – Spring Boot JAR – 缺少EmbeddedServletContainerFacto

发布时间:2020-12-15 02:11:20 所属栏目:Java 来源:网络整理
导读:Spring Boot(1.2.7)Web应用程序(响应SSL请求)在Intellij IDEA上运行良好. 构建JAR工件以从命令行运行,在启动时抛出错误 org.springframework.context.ApplicationContextException: 无法启动嵌入式容器; 嵌套异常是org.springframework.context.Application
Spring Boot(1.2.7)Web应用程序(响应SSL请求)在Intellij IDEA上运行良好.

构建JAR工件以从命令行运行,在启动时抛出错误

org.springframework.context.ApplicationContextException:
无法启动嵌入式容器;
嵌套异常是org.springframework.context.ApplicationContextException:由于缺少EmbeddedServletContainerFactory bean,无法启动EmbeddedWebApplicationContext.

问题

>我该如何避免此错误?
>如果我需要声明一个EmbeddedServletContainerFactory,我怎样才能让它的ServletContainer处理我的Controller请求?

尝试解决方案

按错误请求添加了EmbeddedservletContainerFactory.项目现在从JAR开始,但Controller不会像从IntelliJ运行时那样收到请求.

这是我添加EmbeddedServletContainerFactory后Application.class的样子

package org.coursera.diabetes;

import com.j256.ormlite.dao.Dao;
import com.j256.ormlite.support.ConnectionSource;
import diabetes.common.model.*;
import org.apache.catalina.connector.Connector;
import org.apache.coyote.http11.Http11NioProtocol;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.context.embedded.ConfigurableEmbeddedServletContainer;
import org.springframework.boot.context.embedded.EmbeddedServletContainerCustomizer;
import org.springframework.boot.context.embedded.EmbeddedServletContainerFactory;
import org.springframework.boot.context.embedded.tomcat.TomcatConnectorCustomizer;
import org.springframework.boot.context.embedded.tomcat.TomcatEmbeddedServletContainerFactory;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Profile;
import org.springframework.core.env.Environment;
import org.springframework.core.io.ClassPathResource;
import org.springframework.core.io.Resource;

import java.io.File;
import java.io.IOException;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;

@SpringBootApplication
public class Application {
    private static final Logger logger = LoggerFactory.getLogger(Application.class);

    private static final String dbUrl = "jdbc:h2:mem:testdb";

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

    }

    @Bean
    @Profile("production")
    public EmbeddedServletContainerFactory servletContainer(@Value("${keystore.file}") Resource keystoreFile) {
        TomcatEmbeddedServletContainerFactory tomcat = new TomcatEmbeddedServletContainerFactory();
        //factory.setPort(8443);
        String absoluteKeystoreFile = "";

        try {
            absoluteKeystoreFile = keystoreFile.getFile().getAbsolutePath();
            logger.info(String.format("******** keystore: %s",absoluteKeystoreFile));
        } catch (IOException e) {
            e.printStackTrace();
        }

        tomcat.addAdditionalTomcatConnectors(createSslConnector(absoluteKeystoreFile));
        return tomcat;
    }

    private Connector createSslConnector(String absKeystoreFile) {
        Connector connector = new Connector("org.apache.coyote.http11.Http11NioProtocol");
        Http11NioProtocol protocol = (Http11NioProtocol) connector.getProtocolHandler();
        try {
            connector.setScheme("https");
            connector.setSecure(true);
            connector.setPort(8443);
            protocol.setSSLEnabled(true);
            protocol.setKeystoreFile(absKeystoreFile);
            protocol.setKeystorePass("changeit");
            protocol.setKeyAlias("tomcat");
            return connector;
        }
        catch (Exception ex) {
            throw new IllegalStateException("can't access keystore: [" + "keystore"
                    + "] or truststore: [" + "keystore" + "]",ex);
        }
    }
}

笔记

Spring Boot(Web)应用程序在Intellij IDEA上运行良好,响应https请求,无需在application.properties中执行任何操作:

security.require-ssl=true
server.port=8443
server.ssl.key-store=src/main/resources/private/keystore
server.ssl.key-store-password=changeit
server.ssl.key-password=changeit

要从命令行启动JAR工件,我使用:

java -Dspring.profiles.active=production -Dkeystore.file=file:///$PWD/keystore -jar diabetes-spring.jar

JAR启动时没有错误,但https Web请求(从Intellij工作)只返回Apache / tomcat 404
“请求的资源不可用”.

EDITS

使用-Ddebug运行JAR会输出以下信息(我省略了所有未找到配置文件的DEBUG消息application.properties / application / application-production.properties,这些消息似乎并不相关)

.   ____          _            __ _ _
 / / ___'_ __ _ _(_)_ __  __ _    
( ( )___ | '_ | '_| | '_ / _` |    
 /  ___)| |_)| | | | | || (_| |  ) ) ) )
  '  |____| .__|_| |_|_| |___,| / / / /
 =========|_|==============|___/=/_/_/_/
 :: Spring Boot ::

2015-11-13 14:16:39.980  INFO 47600 --- [           main] org.coursera.diabetes.Applica
tion        : Starting Application on Bakers-MacBook-Pro.local with PID 47600 (/User
s/baker/coursera-android/MoCCA-15/spring-tests/diabetes_root2/diabetes-spring/out/artifa
cts/diabetes_spring_jar/diabetes-spring.jar started by blam in /Users/blam/coursera-and
roid/MoCCA-15/spring-tests/diabetes_root2/diabetes-spring/out/artifacts/diabetes_spring
_jar)
2015-11-13 14:16:39.983 DEBUG 47600 --- [           main] o.s.boot.SpringApplication
            : Loading source class org.coursera.diabetes.Application
2015-11-13 14:16:40.011 DEBUG 47600 --- [           main] o.s.b.c.c.ConfigFileApplicati
onListener  : Activated profiles production
2015-11-13 14:16:40.011 DEBUG 47600 --- [           main] o.s.b.c.c.ConfigFileApplicati
onListener  : Loaded config file 'file:./config/application.properties'
2015-11-13 14:16:40.020  INFO 47600 --- [           main] ationConfigEmbeddedWebApplica
tionContext : Refreshing org.springframework.boot.context.embedded.AnnotationConfigEmbe
ddedWebApplicationContext@23faf8f2: startup date [Fri Nov 13 14:16:40 WET 2015]; root o
f context hierarchy
2015-11-13 14:16:40.022 DEBUG 47600 --- [           main] ationConfigEmbeddedWebApplica
tionContext : Bean factory for org.springframework.boot.context.embedded.AnnotationConf
igEmbeddedWebApplicationContext@23faf8f2: org.springframework.beans.factory.support.Def
aultListableBeanFactory@6cc7b4de: defining beans [org.springframework.context.annotatio
n.internalConfigurationAnnotationProcessor,org.springframework.context.annotation.inter
nalAutowiredAnnotationProcessor,org.springframework.context.annotation.internalRequired
AnnotationProcessor,org.springframework.context.annotation.internalCommonAnnotationProc
essor,application]; root of factory hierarchy
2015-11-13 14:16:40.220 DEBUG 47600 --- [           main] ationConfigEmbeddedWebApplica
tionContext : Unable to locate MessageSource with name 'messageSource': using default [
org.springframework.context.support.DelegatingMessageSource@20ce78ec]
2015-11-13 14:16:40.221 DEBUG 47600 --- [           main] ationConfigEmbeddedWebApplica
tionContext : Using ApplicationEventMulticaster [org.springframework.context.event.Simp
leApplicationEventMulticaster@393671df]
2015-11-13 14:16:40.226  WARN 47600 --- [           main] ationConfigEmbeddedWebApplica
tionContext : Exception encountered during context initialization - cancelling refresh
attempt

org.springframework.context.ApplicationContextException: Unable to start embedded conta
iner; nested exception is org.springframework.context.ApplicationContextException: Unab
le to start EmbeddedWebApplicationContext due to missing EmbeddedServletContainerFactor
y bean.
        at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.onRe
fresh(EmbeddedWebApplicationContext.java:132)
        at org.springframework.context.support.AbstractApplicationContext.refresh(Abstr
actApplicationContext.java:474)
        at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.refr
esh(EmbeddedWebApplicationContext.java:117)
        at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:68
9)
        at org.springframework.boot.SpringApplication.run(SpringApplication.java:321)
        at org.springframework.boot.SpringApplication.run(SpringApplication.java:969)
        at org.springframework.boot.SpringApplication.run(SpringApplication.java:958)
        at org.coursera.diabetes.Application.main(Application.java:40)
Caused by: org.springframework.context.ApplicationContextException: Unable to start EmbeddedWebApplicationContext due to missing EmbeddedServletContainerFactory bean.
        at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.getEmbeddedServletContainerFactory(EmbeddedWebApplicationContext.java:182)
        at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.createEmbeddedServletContainer(EmbeddedWebApplicationContext.java:155)
        at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.onRefresh(EmbeddedWebApplicationContext.java:129)
        ... 7 common frames omitted

2015-11-13 14:16:40.227  INFO 47600 --- [           main] .b.l.ClasspathLoggingApplicationListener : Application failed to start with classpath: [file:/Users/baker/coursera-android/MoCCA-15/spring-tests/diabetes_root2/diabetes-spring/out/artifacts/diabetes_spring_jar/diabetes-spring.jar]
2015-11-13 14:16:40.228 ERROR 47600 --- [           main] o.s.boot.SpringApplication               : Application startup failed

org.springframework.context.ApplicationContextException: Unable to start embedded container; nested exception is org.springframework.context.ApplicationContextException: Unable to start EmbeddedWebApplicationContext due to missing EmbeddedServletContainerFactory bean.
        at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.onRefresh(EmbeddedWebApplicationContext.java:132)
        at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:474)
        at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.refresh(EmbeddedWebApplicationContext.java:117)
        at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:689)
        at org.springframework.boot.SpringApplication.run(SpringApplication.java:321)
        at org.springframework.boot.SpringApplication.run(SpringApplication.java:969)
        at org.springframework.boot.SpringApplication.run(SpringApplication.java:958)
        at org.coursera.diabetes.Application.main(Application.java:40)
Caused by: org.springframework.context.ApplicationContextException: Unable to start EmbeddedWebApplicationContext due to missing EmbeddedServletContainerFactory bean.
        at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.getEmbeddedServletContainerFactory(EmbeddedWebApplicationContext.java:182)
        at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.createEmbeddedServletContainer(EmbeddedWebApplicationContext.java:155)
        at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.onRefresh(EmbeddedWebApplicationContext.java:129)
        ... 7 common frames omitted

解决方法

在IntelliJ IDEA – 项目结构 – 工件 – 可用元素中,需要将所有Gradle依赖库提取到输出根中,以便Spring Boot应用程序的JAR从java命令行执行中正常运行.

将JAR工件更改为此后,我可以构建JAR并从命令行JVM运行它.

对于在HTTPS / SSL端口8443上运行的默认TomcatEmbeddedServletContainerFactory,请指定等于application.properties中所需的java命令行参数.

java -jar your-spring.jar --security.require-ssl=true --server.port=8443 --server.ssl.key-store=keystore --server.ssl.key-store-password=changeit --server.ssl.key-password=changeit

enter image description here

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读