【问题标题】:Trouble running embedded Tomcat from IntelliJ Idea Community从 IntelliJ Idea 社区运行嵌入式 Tomcat 时遇到问题
【发布时间】:2016-04-29 14:54:41
【问题描述】:

我正在尝试使用答案 here 以便在 IntelliJ Idea Community Edition 中从 Oracle 运行 this example。我创建了一个新项目,从示例中复制了源代码并在 Idea 中启用了 Maven 支持。我可以制作并运行该项目,但无法在浏览器中访问该服务。 Tomcat不断抛出404。注意源代码和 pom.xml 文件没有改动。

pom.xml:

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <groupId>com.example.employees</groupId>
    <artifactId>employees-app</artifactId>
    <packaging>war</packaging>
    <version>1.0-SNAPSHOT</version>
    <name>employees-app Maven Webapp</name>
    <url>http://maven.apache.org</url>
    <properties>
        <tomcat.version>7.0.57</tomcat.version>
    </properties>
    <dependencies>
        <dependency>
            <groupId>org.apache.tomcat.embed</groupId>
            <artifactId>tomcat-embed-core</artifactId>
            <version>${tomcat.version}</version>
        </dependency>
        <dependency>
            <groupId>org.apache.tomcat.embed</groupId>
            <artifactId>tomcat-embed-logging-juli</artifactId>
            <version>${tomcat.version}</version>
        </dependency>
        <dependency>
            <groupId>org.apache.tomcat.embed</groupId>
            <artifactId>tomcat-embed-jasper</artifactId>
            <version>${tomcat.version}</version>
        </dependency>
        <dependency>
            <groupId>org.apache.tomcat</groupId>
            <artifactId>tomcat-jasper</artifactId>
            <version>${tomcat.version}</version>
        </dependency>
        <dependency>
            <groupId>org.apache.tomcat</groupId>
            <artifactId>tomcat-jasper-el</artifactId>
            <version>${tomcat.version}</version>
        </dependency>
        <dependency>
            <groupId>org.apache.tomcat</groupId>
            <artifactId>tomcat-jsp-api</artifactId>
            <version>${tomcat.version}</version>
        </dependency>
        <dependency>
            <groupId>jstl</groupId>
            <artifactId>jstl</artifactId>
            <version>1.2</version>
        </dependency>
    </dependencies>
     <build>
        <finalName>employees-app</finalName>
        <resources>
            <resource>
                <directory>src/main/webapp</directory>
                <targetPath>META-INF/resources</targetPath>
            </resource>
        </resources>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <version>2.3.2</version>
                <inherited>true</inherited>
                <configuration>
                    <source>1.8</source>
                    <target>1.8</target>
                </configuration>

            </plugin>           
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-assembly-plugin</artifactId>
                <configuration>
                    <descriptorRefs>
                        <descriptorRef>jar-with-dependencies</descriptorRef>
                    </descriptorRefs>
                    <finalName>employees-app-${project.version}</finalName>
                    <archive>
                        <manifest>
                            <mainClass>com.example.employees.Main</mainClass>
                        </manifest>
                    </archive>
                </configuration>
                <executions>
                    <execution>
                        <phase>package</phase>
                        <goals>
                            <goal>single</goal>
                        </goals>
                    </execution>
                </executions>
            </plugin>
        </plugins>
    </build>
</project>

使用 Process Monitor 我已经能够确定 Tomcat 将网站的根目录 (localhost:8080) 与 MyProject\target\classes 相关联。如果我在其中放置一个虚拟 txt 文件,我可以通过浏览器访问它(例如 localhost:8080/test.txt)。

“类”目录不为空。它包含两个子目录:

  1. com/example/employees/*.class - 所有类文件
  2. META-INF/resources/[Oracle example ] 中 /main/src/webapp 中的所有内容

我的直觉是输出的文件夹层次结构有问题。我不确定是什么或如何解决它。有什么想法吗?

【问题讨论】:

  • 您是否尝试按照官方doc 中的说明运行示例?从命令行(在 mvn clean package 之后),从目标文件夹运行:java -jar employees-app-1.0-SNAPSHOT-jar-with-dependencies.jar 然后检查 localhost:8080
  • 不,我没有。目标是能够使用 IntelliJ 进行 Tomcat 开发。

标签: java maven tomcat intellij-idea


【解决方案1】:

我想通了。

正如链接的帖子所示,最好使用 Heroku 的启动器和 pom.xml 文件。

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
  <modelVersion>4.0.0</modelVersion>
  <groupId>com.heroku.sample</groupId>
  <artifactId>embeddedTomcatSample</artifactId>
  <version>1.0-SNAPSHOT</version>
  <packaging>jar</packaging>
  <name>embeddedTomcatSample Maven Webapp</name>
  <url>http://maven.apache.org</url>
  <properties>
    <tomcat.version>8.0.28</tomcat.version>
  </properties>
  <dependencies>
    ...tomcat & other deps...
  </dependencies>
  <build>
    <finalName>embeddedTomcatSample</finalName>
    <plugins>
        <plugin>
            <groupId>org.codehaus.mojo</groupId>
            <artifactId>appassembler-maven-plugin</artifactId>
            <version>1.1.1</version>
            <configuration>
                <assembleDirectory>target</assembleDirectory>
                <programs>
                    <program>
                        <mainClass>launch.Main</mainClass>
                        <name>webapp</name>
                    </program>
                </programs>
            </configuration>
            <executions>
                <execution>
                    <phase>package</phase>
                    <goals>
                        <goal>assemble</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>
    </plugins>
  </build>
</project>

这个启动器功能通过以编程方式将 Tomcat 配置为在项目目录中运行来完成大部分的魔法。

public static void main(String[] args) throws Exception {

        String webappDirLocation = "src/main/webapp/";
        Tomcat tomcat = new Tomcat();

        //The port that we should run on can be set into an environment variable
        //Look for that variable and default to 8080 if it isn't there.
        String webPort = System.getenv("PORT");
        if(webPort == null || webPort.isEmpty()) {
            webPort = "8080";
        }

        tomcat.setPort(Integer.valueOf(webPort));

        StandardContext ctx = (StandardContext) tomcat.addWebapp("/", new File(webappDirLocation).getAbsolutePath());
        System.out.println("configuring app with basedir: " + new File("./" + webappDirLocation).getAbsolutePath());

        // Declare an alternative location for your "WEB-INF/classes" dir
        // Servlet 3.0 annotation will work
        File additionWebInfClasses = new File("target/classes");
        WebResourceRoot resources = new StandardRoot(ctx);
        resources.addPreResources(new DirResourceSet(resources, "/WEB-INF/classes",
                additionWebInfClasses.getAbsolutePath(), "/"));
        ctx.setResources(resources);

        tomcat.start();
        tomcat.getServer().await();
    }

我不知道如何以编程方式设置 Tomcat 的 conf 文件夹的路径,但感谢this answer,我能够克服这个问题。在正常情况下,Tomcat 负责设置初始上下文。因此,webapp 的 context.xml 文件中的环境变量最终会出现在初始上下文中。幸运的是,可以通过自定义 InitialContextFactory 复制它。

【讨论】:

    猜你喜欢
    • 2014-03-29
    • 1970-01-01
    • 2013-08-17
    • 1970-01-01
    • 2023-03-12
    • 1970-01-01
    • 1970-01-01
    • 2018-03-07
    • 2019-02-27
    相关资源
    最近更新 更多