Mar 8, 2018 2:27:03 PM seb leridon avatar   565

Construction and assembly: the builds

A web portal lutece is a webapp java EE. The content of this webapp (JSP, java classes, HTML templates, etc.) comes directly from the core of Lutece (required) and plugins (optional). The assembly of a webapp from the core and the list of plugins is done with the Maven tool (https://maven.apache.org/). Before proceeding further in this chapter, it is necessary to know how Maven works: we can start with reading from https://maven.apache.org/users/index.html.

In addition to a classic use of Maven, the assembly of webapps Lutece relies on:

  • two POMs parents lutece-global-pom (for "lutece-core" and "lutece-plugin") and lutece-site-pom (for "lutece-site"). These POMs group the default configurations of lutece projects.
  • a Maven plugin: lutece-maven-plugin. This Lutece-specific Maven plugin looks like the maven-war-plugin. To understand the use of lutece-maven-plugin, it is recommended to know maven-war-plugin (https://maven.apache.org/plugins/maven-war-plugin/).

Assembling a webapp lutece

The architecture of the lutece project is to build a webapp containing the full functionality of the chosen plugins. To do this, lutece-core contains the mandatory files of a webapp (for example WEB-INF / web.xml) and the files that are used for features common to all plugins (java code, header and footer html pages, etc. .). The plugins bring in addition their own files. In addition, it is sometimes necessary for a given site to be able to modify some files present in lutece-core or in a lutece-plugin (for example, modify a template html). The main goal of assembling a webapp lutece is therefore to produce the right files from the different sources to be included in the final webapp. We will see how lutece-maven-plugin achieves this goal.

However, apart from the assembly of webapps, the use of maven also makes it possible to reach other objectives: to manage the compilation and the tests of the code, to be able to publish artifacts providing a reusable functionality, to generate the technical documentation (javadoc and Maven Site), etc.

Maven provides as standard a plugin that partially meets the main goal of assembling webapps described in the previous paragraph: maven-war-plugin. Lutece-maven-plugin is inspired by maven-war-plugin:

  • it compiles the code and places it in the "WEB-INF / classes" folder of the webapp,
  • it copies the files from the webapp to the root of the webapp,
  • It copies the content (compiled code or webapp files) dependencies.

Lutece-maven-plugin looks like maven-war-plugin on the following:

  • It manages two folders "src" (for the code to be compiled) and "webapp" for the files to copy in the webapp. With the exception of the "package" phase, which we will discuss below, it associates the same maven goals with the standard lifecycle phases (java compilation, tests, deployment, etc.), which makes it possible to publish artifacts on the repositories normally. maven.
  • It provides goals maven to get the webapp in version "war" or version "exploded" or (for the artifact lutece-core only) version "inplace".
  • It shares configuration options (eg finalName and outputDirectory).
  • It copies the dependencies of type jar in the WEB-INF / lib folder of a complete webapp.
  • It assembles webapps using a concept similar to overlays from dependencies.

Lutece-maven-plugin differs from maven-war-plugin on the following:

  • The maven-war-plugin plugin uses a structure "src / main / java" and "src / webapp" to separate code and files from the webapp. The lutece-maven-plugin plugin uses "src / java" and "webapp /".
  • Lutece-maven-plugin does not use artifact type "war", but defines several types of artifacts maven that correspond to the different elements of the lutece architecture: lutece-core, lutece-plugin, lutece-site. Lutece-core and lutece-plugin are artifacts that contain java classes to compile and files to copy in the webapp (in the manner of "war" type artifacts for maven-war-plugin). Lutece-site contains only files to copy in the webapp, overloading those coming from artifacts lutece-core or lutece-plugin.
  • The default goal for the "package" phase does not produce the entire webapp, only the files from this artifact. Other goals must be invoked to get the full webapp.
  • Unlike maven-war-plugin, the concept of overlay is central and its systematic use in lutece-maven-plugin: we can produce a functional webapp from any type of lutece-core artifact, lutece- plugin or lutece-site. The webapp will contain all the files coming from the artifact and its dependencies (compiled classes, webapp files).
  • The full webapp will also contain files from two special folders: defaultConfDirectory and localConfDirectory: defaultConfDirectory defaults to "src / conf / default". Lutece-site-pom defines maven profiles that change the defaultConfDirectory value to "src / conf / <profile>": "dev", "rec", "integ", "training", "preprod", "prod". localConfDirectory defaults to "$ HOME / lutece / conf / <artifactId>". Be careful, these files do not come from an artifact maven, so they cause non-reproducible assemblies. They must be used sparingly.
  • The reactor maven (multi module mode) is handled in a very different way from a conventional multi module maven project, as we will see later.

These differences make it possible to have a flexible system where one can manage a large number of Maven artifacts and thus write very modular components.

Rules of use of lutece-maven-plugin

The maven goals used

We will use the following goals of lutece-maven-plugin:

  • lutece:exploded for lutece-core and lutece-plugin
  • lutece:site-assembly for lutece-site

Overload order of the files

Lutece-maven-plugin uses a pervasive concept similar to maven-war-plugin overlays. It is important to know in which order overlays are applied to know which file is used when a file is present in several sources. This concerns only the files of the webapp (for example in the "webapp /" folder of a lutece-plugin) and an assembly without maven modules. The order is:

  • lutece-core or lutece-plugin dependencies
  • "webapp" folder of the current artifact
  • defaultConfDirectory of the current artifact
  • localConfDirectory of the current artifact

The version used will be the one present in the last element of this list.

Note: There is no defined order between the two dependency files, so one file must not exist in two different dependencies.

For multi-module assembly, the order depends on the order of the artifacts in the reactor.

Examples of use of lutece-maven-plugin

Assembling a lutece-site

The simplest use of lutece-maven-plugin is to build a Lutece-site artifact without plugins or overload. The project then contains only a pom.xml file at the root. This POM contains:

  • The definition of the maven repositories of lutece (to get the parent POM and the maven plugin)
  • the link to the parent POM
  • addiction to the lutece-core artifact

Maven will download the lutece-core artifact from the repositories and make the webapp from this artifact.

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<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/maven-v4_0_0.xsd">
    <parent>
        <artifactId>lutece-site-pom</artifactId>
        <groupId>fr.paris.lutece.tools</groupId>
        <version>2.0.4</version>
    </parent>
    <modelVersion>4.0.0</modelVersion>
    <groupId>com.example</groupId>
    <artifactId>lutece-example</artifactId>
    <packaging>lutece-site</packaging>
    <name>Lutece example</name>
    <version>1.0.0</version>
    <repositories>
        <repository>
            <snapshots>
                <enabled>true</enabled>
            </snapshots>
            <id>luteceSnapshot</id>
            <name>luteceSnapshot</name>
            <url>http://dev.lutece.paris.fr/snapshot_repository</url>
        </repository>
        <repository>
            <snapshots>
                <enabled>false</enabled>
            </snapshots>
            <id>lutece</id>
            <name>luteceRepository</name>
            <url>http://dev.lutece.paris.fr/maven_repository</url>
        </repository>
    </repositories>
    <dependencies>
        <dependency>
            <groupId>fr.paris.lutece</groupId>
            <artifactId>lutece-core</artifactId>
            <version>5.0.0</version>
            <type>lutece-core</type>
        </dependency>
    </dependencies>
</project>

We assemble the webapp using the maven goal:

$ mvn lutece:site-assembly

This produces the webapp in version "war" and "exploded" in the folder target:

$ ls target/lutece-example-1.0.0 lutece-example-1.0.0.war

You can also activate maven profiles during this goal to use a different defaultConfDirectory:

$ mvn lutece:site-assembly -P prod

Assembling a lutece-plugin or lutece-core

By using the pom.xml of the project we want to assemble, we can produce a webapp with the command:

$ git clone https://github.com/lutece-platform/lutece-core
$ cd lutece-core
$ mvn lutece:exploded

The webapp version "exploded" is available in the folder target / lutece /

Using the local maven repository

To simply propagate the changes made to an artifact in an assembled webapp from another artifact, you can use the local maven repository with the maven "install" command

$ cd /lutece-core
$ mvn install
$ cd /plugin
$ mvn clean lutece:exploded

Using the Maven Reactor (multi module)

To avoid having to use maven install on all dependencies, you can use the maven modules and the reactor. Attention, the use of maven modules is very special with lutece-maven-plugin and is used only with the goal "lutece:exploded". The multi-module mode assembles a webapp from the different artifacts of the reactor in the "target / lutece" folder at the pom aggregator level. We can not use artifact lutece-site in this kind of assembly. Contrary to a classic use of the reactor where the last modules produce the desired artifacts, lutece-maven-plugin directly assembles all the modules in the target folder of the pom aggregator during the reactor processing.

We can use the following project structure where we have the different projects coming from github and the global-pom:

├── lutece-core
├── lutece-search-library-lucene
├── lutece-system-plugin-systeminfo
└── pom.xml

By convention, we define modules when the "multi-project" profile is activated by adding this to global-pom pom.xml:

<Profiles>
 <Profile>
  <Id> multi-project </id>
  <Modules>
   <Module> Lutece-core </module>
   <Module> Lutece-system-plugin-systeminfo / </module>
   <Module> Lutece-search-library-lucene </module>
  </Modules>
 </Profile>
</Profiles>

We can then assemble the webapp:

$ mvn lutece:exploded -P multi-project
 [INFO] ----------------------------------------------- -------------------------
 [INFO] Reactor Summary:
 [INFO]
 [INFO] Lutece global pom ................................. SUCCESS [1.238s]
 [INFO] Lutece Analyzers and Indexers ..................... SUCCESS [2.000s]
 [INFO] Lutece ............................................ SUCCESS [ 4.659s]
 [INFO] Lutece systeminfo plugin .......................... SUCCESS [0.325s]
 [INFO] ----------------------------------------------- -------------------------
 [INFO] BUILD SUCCESS
 [INFO] ----------------------------------------------- -------------------------

The webapp is available in the "target / lutece" folder

Note: beware, because of the particularities of lutece-maven-plugin in multi-modules, to clean and recompile all in one command you must use:

$ mvn lutece:clean lutece:exploded -P multi-project