web-dev-qa-db-fra.com

L'application Web de démarrage de printemps ne fonctionne pas sur Tomcat 9

Mon application Web fonctionne correctement sur Eclipse Photon STS, Java 8 et Spring Boot 2.02 avec Tomcat intégré à l'aide du terminal:

http://localhost:8081/DataViewer/tspsPatentSearch

Mais lorsque je compile le code dans le fichier DataViewer.war (à l'aide du package mvn) et que je l'exécute sur Tomcat 9 sous Linux Avec un noeud final:

http://myserver.com:8081/DataViewer/tspsPatentSearch

Je reçois l'infâme:

Whitelabel Error Page
There was an unexpected error (type=Not Found, status=404).
/DataViewer/tspsPatentSearch

Mon fichier pom.xml est: 

`<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/xsd/maven-4.0.0.xsd"><modelVersion>4.0.0</modelVersion>
<groupId>com.clarivate</groupId>
<artifactId>dataviewer</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>war</packaging>

<name>dataviewer</name>

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>2.0.2.RELEASE</version>
    <relativePath/> <!-- lookup parent from repository -->
</parent>

<properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
    <Java.version>1.8</Java.version>
    <start-class>com.clarivate.dataviewer.DvMain</start-class>
</properties>

<dependencies>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
            <exclusions>
                <exclusion>
                    <groupId>org.springframework.boot</groupId>
                    <artifactId>spring-boot-starter-Tomcat</artifactId>
                </exclusion>
            </exclusions>
    </dependency>

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-Tomcat</artifactId>
        <scope>provided</scope>
    </dependency>

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
        <scope>test</scope>
    </dependency>

    <!-- DS may need to remove for Tomcat installation -->
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-web</artifactId>
    </dependency>

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-log4j2</artifactId>
        <exclusions>
            <exclusion>
                <groupId>org.Apache.logging.log4j</groupId>
                <artifactId>log4j-slf4j-impl</artifactId>
            </exclusion>
        </exclusions>
    </dependency>

   <dependency>
        <groupId>org.Apache.Tomcat.embed</groupId>
        <artifactId>Tomcat-embed-jasper</artifactId>
        <scope>provided</scope>
    </dependency>

    <dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>jstl</artifactId>
    </dependency>

    <dependency>
        <groupId>com.Oracle</groupId>
        <artifactId>ojdbc6</artifactId>
        <version>11.2.0.1.0</version>
    </dependency>


    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-jdbc</artifactId>
    </dependency>
    <dependency>
        <groupId>com.h2database</groupId>
        <artifactId>h2</artifactId>
        <scope>test</scope>
    </dependency>

</dependencies>

   <!-- Required to find ojdbc6, because Oracle don't make it available to maven-->
    <repositories>
        <repository>
          <id>codelds</id>
          <url>https://code.lds.org/nexus/content/groups/main-repo</url>
        </repository>
      </repositories>

<build>
    <finalName>DataViewer</finalName>
    <plugins>
        <plugin>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-maven-plugin</artifactId> 
            <configuration>
                <mainClass>com.clarivate.dataviewer.DvMain</mainClass>
            </configuration>    
        </plugin>
    </plugins>
</build>


<description>TSPS data viewer</description>

Dans application.properties j'ai:

spring.mvc.view.prefix=/WEB-INF/jsp/
spring.mvc.view.suffix=.jsp
server.servlet.path=/DataViewer 

Mon cours principal est:

package com.clarivate.dataviewer;
import org.Apache.logging.log4j.Logger;
import org.Apache.logging.log4j.LogManager;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.builder.SpringApplicationBuilder;
import org.springframework.boot.web.servlet.support.SpringBootServletInitializer;

@SpringBootApplication

public class DvMain extends SpringBootServletInitializer {

    static Logger logger = LogManager.getRootLogger();

    public static void main(String[] args) {
        logger.debug("DS1A in main()");
        SpringApplication.run(DvMain.class, args);
        logger.info("DS1C finished.");
    }


    //@Override
    protected SpringApplicationBuilder configure(SpringApplicationBuilder builder) {
        return builder.sources(DvMain.class);
     }  
}

Mon MainController.Java a:

@GetMapping("/tspsPatentSearch")
public String tspsPatentSearch(Model model) {
     model.addAttribute("tspsPatent", new TspsPatent());

     return "tspsPatentSearch";                 
}

Le fichier war décompresse très bien et il n'y a pas d'erreur. En catalina.out nous avons:

2018-10-04 12:09:09.954  INFO 12950 --- [           main] s.w.s.m.m.a.RequestMappingHandlerMapping : Mapped "{[/tspsPatentSearch],methods=[POST]}" onto public Java.lang.String com.clarivate.dataviewer.controller.MainController.tspsPatentSearch(com.clarivate.dataviewer.model.TspsPatent,org.springframework.ui.Model,org.springframework.validation.BindingResult)

et pas d'erreurs. J'ai essayé this c'est-à-dire que ma structure de paquet est correcte et this que mes jsp sont à l'emplacement correct (data_viewer\src\main\webapp\WEB-INF\jsp) Et Je suis maintenant à court d'idées. Toute aide très appréciée

Edit: Si je copie tspsPatentSearch.jsp dans le répertoire principal du fichier war, Tomcat le trouve. Donc, il semblerait que Tomcat ignore:

spring.mvc.view.prefix=/WEB-INF/jsp/

ou ne pas trouver application.properties du tout.

4
DS.

Ajoutez ceci à votre application.properties:

server.servlet.contextPath=/

J'ai pris votre exemple de code et, en supposant que vous avez annoté votre MainController simplement en tant que @Controller, assemblé un déploiement. J'ai changé quelques petites choses, mais je crois que c'est le moment qui l'a fait. Je n'ai pas trouvé de références expliquant pourquoi cela pourrait être requis par Tomcat, mais j'ai bien l'intention de continuer à chercher. Je vous tiendrai au courant si je trouve quelque chose.

Modifier:

J'ai remarqué quelques journalisations en double au printemps 2.0.2 liées à ce problème: https://github.com/spring-projects/spring-boot/issues/13470

Le problème est apparu corrigé dans la version 2.0.4, donc j'ai mis à jour.

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>2.0.4.RELEASE</version>
    <relativePath /> <!-- lookup parent from repository -->
</parent>

De plus, j'ai supprimé l'entrée server.servlet.contextPath=/ et tada Je peux toujours atteindre le jsp Hello World que j'ai configuré. Si la mise à niveau vous est possible, vous pourriez peut-être essayer avant d'ajouter quelque chose à application.properties qui pourrait être considéré comme une fonctionnalité dupliquée. Au moins, je peux vous promettre une meilleure expérience de journalisation.

Edit # 2:

Aucune arme à feu, jusqu'à présent, mais ceux-ci (à partir de 2.0.4) pourraient être liés:

Fournit un moyen cohérent de découvrir le chemin d'accès principal du DispatcherServlet

Les servlets Dispatcher avec un nom de servlet personnalisé ne sont pas trouvés par le noeud final de mappages

Rien ne semblait probable sur un balayage de surface de 2.0.3. Je vais me reposer pour le moment et vous donner une chance d'essayer quelques trucs. Bonne chance!

Edit # 3:

Je suis désolé de continuer à vous suggérer de changer d’environnement, mais une différence que j’ai constatée entre ce que j’ai testé et celui avec lequel vous travaillez est que vous semblez utiliser Tomcat-9.0.0.M20 alors que j’essayais avec 9.0.12 .

Que vous souhaitiez mettre à niveau ou non, quelques points à noter et/ou à faire:

1) Mettez à jour votre question avec ce que vous avez maintenant si elle est différente d’avant. Incluez le server.servlet.contextPath=/ dans votre application.properties pour que tous les autres à la recherche puissent voir ce que vous avez fait.

2) L'exclusion que vous avez pour spring-boot-starter-Tomcat sous spring-boot-starter-web ne semble rien faire - vous pouvez vérifier en comparant le résultat de l'exécution de mvn dependency:tree avant et après la suppression.

3) Je ne suis pas sûr que votre dépendance spring-web soit nécessaire non plus, car elle est importée par défaut sous le spring-boot-starter.

4) Maintenant à votre sortie. Spring Boot est à venir (notez la bannière) et vos classes sont retrouvées et traitées.

catalina.out.DEBUG également dans votre DS.log à partir de ~ 08: 35: 38.162

2018-10-12 09:30:17.322 DEBUG 55745 --- [           main] o.s.c.a.ClassPathBeanDefinitionScanner   : Identified candidate component class: file [/data/apps/Tomcat/Apache-Tomcat-9.0.0.M20/webapps/DataViewer/WEB-INF/classes/com/clarivate/dataviewer/controller/MainController.class]
2018-10-12 09:30:17.328 DEBUG 55745 --- [           main] o.s.c.a.ClassPathBeanDefinitionScanner   : Identified candidate component class: file [/data/apps/Tomcat/Apache-Tomcat-9.0.0.M20/webapps/DataViewer/WEB-INF/classes/com/clarivate/dataviewer/database/ReadFromDb.class]
2018-10-12 09:30:17.356 DEBUG 55745 --- [           main] o.s.c.a.ClassPathBeanDefinitionScanner   : Identified candidate component class: file [/data/apps/Tomcat/Apache-Tomcat-9.0.0.M20/webapps/DataViewer/WEB-INF/classes/com/clarivate/dataviewer/service/FileFuncs.class]
2018-10-12 09:30:17.357 DEBUG 55745 --- [           main] o.s.c.a.ClassPathBeanDefinitionScanner   : Identified candidate component class: file [/data/apps/Tomcat/Apache-Tomcat-9.0.0.M20/webapps/DataViewer/WEB-INF/classes/com/clarivate/dataviewer/service/StringFuncs.class]
...
2018-10-12 09:30:19.417  INFO 55745 --- [           main] s.w.s.m.m.a.RequestMappingHandlerMapping : Mapped "{[/tspsPatentSearch],methods=[POST]}" onto public Java.lang.String com.clarivate.dataviewer.controller.MainController.tspsPatentSearch(com.clarivate.dataviewer.model.TspsPatent,org.springframework.ui.Model,org.springframework.validation.BindingResult)
2018-10-12 09:30:19.417  INFO 55745 --- [           main] s.w.s.m.m.a.RequestMappingHandlerMapping : Mapped "{[/tspsPatentSearch],methods=[GET]}" onto public Java.lang.String com.clarivate.dataviewer.controller.MainController.tspsPatentSearch(org.springframework.ui.Model)
...
2018-10-12 09:30:19.769  INFO 55745 --- [           main] com.clarivate.dataviewer.DvMain          : Started DvMain in 3.125 seconds (JVM running for 5.845)

Et je note effectivement le mappage sur /error renvoyé pour votre demande à 09:32:11.

Je trouve cela étrange:

2018-10-12 09:32:11.758 DEBUG 55745 --- [nio-8081-exec-1] o.s.web.servlet.DispatcherServlet        : DispatcherServlet with name 'dispatcherServlet' processing GET request for [/DataViewer/DataViewer/error]

Et c'est différent dans DS.log:

2018-10-12 08:36:56.136 DEBUG 6992 --- [nio-8081-exec-1] o.s.web.servlet.DispatcherServlet        : DispatcherServlet with name 'dispatcherServlet' processing GET request for [/DataViewer /error]

Plus précisément /DataViewer/DataViewer/error - avez-vous essayé de demander http: // localhost: 8081/DataViewer/DataViewer/tspsPatentSearch

En général, cela semble être comme si tout allait venir, mais il y a une mauvaise configuration quelque part qui ne permet pas à une demande de mapper au gestionnaire.

0
Jon Sampson

Pour confirmer. Tomcat ajoute le nom du fichier war au point de fin. Par conséquent, si nous créons DataViewerX.war et définissons:

server.servlet.path=/DataViewer

alors le point final lors de l'exécution sur un Tomcat externe est:

myServer.com/DataViewerX/DataViewer/tspsPatentSearch 

mais quand nous courons sur Eclispe, en utilisant le code source, alors le point final est:

http://localhost:8081/DataViewer/tspsPatentSearch

ce qui est un peu ennuyeux mais pas un problème majeur. Une solution consiste à appeler le fichier war ROOT.war, puis Tomcat ignore le nom du fichier war et les deux extrémités sont identiques, mais j'ai plusieurs fichiers war dans le répertoire webapps, de sorte que cette solution ne me convient pas. Si quelqu'un sait comment permettre aux 2 points finaux d'être identiques, dites-le-moi, mais ce n'est pas si important.

1
DS.