Monday, July 6, 2015

Maven Tips



https://maven.apache.org/plugins/maven-resources-plugin/examples/filter.html
https://rterp.wordpress.com/2012/03/16/stamping-version-number-and-build-time-in-properties-file-with-maven/
<resources>
   <resource>
      <directory>src/main/resources</directory>
      <filtering>true</filtering>
   </resource>
</resources>
http://samulisiivonen.blogspot.com/2012/01/cleanin-up-maven-dependencies.html
https://github.com/siivonen/maven-cleanup
The full build time in my project is 1,5 hours and I wanted to eliminate unneeded directdependencies so I decided to make the builds non recursive.

  ./remove-extra-dependencies.rb pom.xml 'mvn clean install -N'

The default behaviour of the plugin is to first resolve the entire dependency tree, then delete the contents from the local repository, and then re-resolve the dependencies from the remote repository.
  1. mvn dependency:purge-local-repository
http://stackoverflow.com/questions/30571/how-do-i-tell-maven-to-use-the-latest-version-of-a-dependency
This answer applies to Maven 2 only! The mentioned LATEST and RELEASE metaversions have been dropped in Maven 3 "for the sake of reproducible builds", over 6 years ago.

When you depend on a plugin or a dependency, you can use the a version value of LATEST or RELEASE. LATEST refers to the latest released or snapshot version of a particular artifact, the most recently deployed artifact in a particular repository. RELEASE refers to the last non-snapshot release in the repository. In general, it is not a best practice to design software which depends on a non-specific version of an artifact. If you are developing software, you might want to use RELEASE or LATEST as a convenience so that you don't have to update version numbers when a new release of a third-party library is released. When you release software, you should always make sure that your project depends on specific versions to reduce the chances of your build or your project being affected by a software release not under your control. Use LATEST and RELEASE with caution, if at all.
The dependency:build-classpath mojo

This goal will output a classpath string of dependencies from the local repository to a file or log and optionally attach and deploy the file. For instance, the file would contain a classpath string like this:
  1. /home/foo/.m2/repository/org/java/utils/util/util-1.0.jar:/home/foo/.m2/ ....
verbose Whether to include omitted nodes in the serialized dependency tree. Notice this feature actually uses Maven 2 algorithm and may give wrong results when used with Maven 3.
Compilation went fine in our case and at runtime it failed due to some class not found exception because the same class was not available in 3.1.3.RELEASE as it was bundled by maven during packaging it as a war.
Maven works on the principle of nearest wins strategy while resolving the dependency conflicts, that   means whichever version it finds nearer in the tree, it will take that version and ignore the other versions. Actually I should say Maven is little bit lazy type of guy , so whenever it starts looking for a dependency it starts traversing the tree from the root and whichever version it found earlier , it will select that and returns from their without going further . If it goes further their might be a chance that it can find some newer version but as it returns from there and take the older version with it to resolve the dependencies L . Honestly speaking it is not a fault of maven because he wants to finish the job as soon as possible and have some rest. Most importantly he(maven) doesn’t know which version your application is expecting so Maven will say to you , Hey , it is yours responsibility to let me know which version you want and if you don’t tell me I will work my own way i.e. nearer the better.
mvn dependency:tree -Dverbose -Dincludes=spring-expression
  • Solution 1 : The very first solution came to my mind is that somehow I have to make this version disappear from the hierarchy before Maven reaches it . In terms of Maven I have to exclude it from the source who is bringing in this version of dependency. In my case it was coming from the spring-security-core jar, so to exclude it from this I did like something this ; Maven Dependency Version Conflicts-1      This solution worked for me, but it has its own limitations like suppose if in future    another artifact brings in the same dependency of the same other version and maven found it nearer then again my application will start breaking , so to fix this again I have to add the exclusion filter in the dependency . I really don’t want to do that and it will be almost impossible to maintain those dependencies in future. So, we opted the second solution and till now it is working good .
  • Solution 2 : As per this approach you can tell maven that you should use this version or a subset of this version while resolving the versions conflicts. The way of telling is you can define that artifact under dependencyManagement and while resolving the version Maven will consult dependencyManagement to check if it have any version information for that dependency or not, if it have then it will use the same version or subset of versions to resolve otherwise it will go by his book of resolving conflicts (nearer the better). So, this way I have defined the version that I want maven to use while resolving the conflicts.Maven Dependency Version Conflicts-2After this it worked like charm and everywhere in the application it was using the version that I have specified. I am not sure whether this is best solution to this problem, it might possible that some more intuitive solution exists for this problem.
If you have noticed that I have said that subset of this version, what I mean to say in version attribute you can also define the range also that will ask Maven to accept any version that is available in this range. Something like this –
<version>[1.0,)  </version>
Since Maven resolves version conflicts with a nearest-wins strategy
The problem is: my direct dependency spring-security-web has a dependency on the version 3.0.7 of aop. So this version of aop is a 2. level dependency for us. My other direct dependency spring-webmvc has a dependency on spring-web, which has a dependency on the version 3.2.4 of aop. Here the newer version of aop is a 3. level dependency for us. Since Maven resolves version conflicts with a nearest-wins strategy, in our example wins the aop 3.0.7 based on this rule. Therefore we have the warning “omitted for conflict with 3.0.7” beside the 3.2.4 version. If spring-webmvc were directly dependent on the 3.2.4 version, they would be on the same level, and in that case maven would resolve this conflict by simply using the one, which has a higher position in pom.
We should be aware of what exaclty we are using, consciously decide which version we should use and resolve this conflict by defining a dependencyManagement sector in our pom.

    <dependencies>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-aop</artifactId>
            <version>${org.springframework.version}</version>
        </dependency>
    </dependencies>
  1. mvn archetype:generate -DgroupId=com.mycompany.app -DartifactId=my-app -DarchetypeArtifactId=maven-archetype-quickstart -DinteractiveMode=false

run mvn dependency:copy-dependencies and you will find target/dependencies folder filled with all the dependencies, including transitive.
You can use the tree goal of the Maven dependency plugin to display all transitive dependencies in your project and look for dependencies that say "omitted for conflict".1
mvn dependency:tree -Dverbose
mvn dependency:tree -Dverbose | grep 'omitted for conflict'
Once you know which dependency has version conflicts, you can use the includes parameter to show just dependencies that lead to that one to see how a particular dependency is being pulled in
To actually resolve the conflict, in some cases it may be possible to find a version of the transitive dependency that both of your primary dependencies will work with. Add the transitive dependency to the dependencyManagement section of your pom and try changing the version until one works.
You could use the maven-enforcer-plugin in your pom to force specific versions of the transitive dependencies. This would help you prevent omissions by the pom configuration when there are conflicts.
This is what worked for me, and I was able to change the versions to match. If you are unable to change versions, then this won't be very helpful.
<project>
...
  <build>
    <plugins>
      ...
      <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-enforcer-plugin</artifactId>
        <version>1.4</version>
        <executions>
          <execution>
            <id>enforce</id>
            <configuration>
              <rules>
                <dependencyConvergence/>
              </rules>
            </configuration>
            <goals>
              <goal>enforce</goal>
            </goals>
          </execution>
        </executions>
      </plugin>
      ...
    </plugins>
  </build>
  ...
</project>
Force a version on the dependency using brackets:
<dependency>
        <groupId>org.slf4j</groupId>
        <artifactId>slf4j-api</artifactId>
        <scope>compile</scope>
        <version>[1.0.0]</version>
</dependency>
Configure it like this:
<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-enforcer-plugin</artifactId>
    <version>1.0</version>
    <executions>
        <execution>
            <id>enforce</id>
            <configuration>
                <rules> 
                    <DependencyConvergence />
                </rules>
            </configuration>
            <goals> 
                <goal>enforce</goal>
            </goals>
        </execution>
    </executions>
</plugin>
This combination of dependencies will cause a build to fail:
  <dependencies>
    <dependency>
      <groupId>org.slf4j</groupId>
      <artifactId>slf4j-jdk14</artifactId>
      <version>1.6.1</version>
    </dependency>
    <dependency>
      <groupId>org.slf4j</groupId>
      <artifactId>slf4j-nop</artifactId>
      <version>1.6.0</version>
    </dependency>
  </dependencies>  
With this being logged during compilation:
[ERROR]
Dependency convergence error for org.slf4j:slf4j-api:1.6.1 paths to dependency are:
+-org.myorg:my-project:1.0.0-SNAPSHOT
  +-org.slf4j:slf4j-jdk14:1.6.1
    +-org.slf4j:slf4j-api:1.6.1
and
+-org.myorg:my-project:1.0.0-SNAPSHOT
  +-org.slf4j:slf4j-nop:1.6.0
    +-org.slf4j:slf4j-api:1.6.0
The Maven Dependency Plugin will help, especially the dependency:analyze goal:
dependency:analyze analyzes the dependencies of this project and determines which are: used and declared; used and undeclared; unused and declared.
Another thing that might help to do some cleanup is the Dependency Convergence report from the Maven Project Info Reports Plugin.

Variables can be included in your resources. These variables, denoted by the ${...} delimiters, can come from the system properties, your project properties, from your filter resources and from the command line.
https://maven.apache.org/plugins/maven-resources-plugin/examples/filter.html
  1. <resource>
  2. <directory>src/main/resources</directory>
  3. <filtering>true</filtering>
  4. </resource>
-q,--quiet Quiet output - only show errors
I think the questioner is looking for -o or --offline option for mvn. This is a command line option and can be provided while executing.
https://developer.jboss.org/wiki/Mavensettingsxmlmaskingpassword?_sscc=t
Let us assume you have multiple repositories for which you have different passwords. Irrespective of how many passwords you have, you need to create a master password.

  1. Create a master password and encrypt it.
  2. Create a ~/.m2/settings-security.xml file
  3. Encrypt your password

Step 1:  Create a master password and encrypt it


  1. $> mvn --encrypt-master-password  somemasterpassword  
  2. {nDpn1bE1vX4HABCDEFGOriBubJhppqAOuy4=}  


Please remember to change "somemasterpassword" to whatever master password you want to remember

Step 2: Create a  ~/.m2/settings-security.xml file


Transfer the encrypted master password into this file.

  1. <settingsSecurity>  
  2.   <master>{jSMOWnoPFgsHVpMvz5VrIt5kRbzGpI8u+9EF1iFQyJQ=}</master>  
  3. </settingsSecurity>   

Step 3: Encrypt your repository password. You can encrypt as many passwords as you please.



  1. mvn --encrypt-password  mysweetlittlepassword  
  2. {X/Mnlwkfm90HVsadbsadsadlsakdsalfdlfdhfldsfldslE3LQ8g4=}  
https://maven.apache.org/guides/mini/guide-encryption.html#Tips
mvn --encrypt-master-password
And then I create ${user.home}/.m2/settings-security.xml with the following content:
  1. <settingsSecurity>
  2. <relocation>/Volumes/mySecureUsb/secure/settings-security.xml</relocation>
  3. </settingsSecurity>
First password is used to generated the master password only, then you can forget it. It is generated using encryption mechanisms and pseudo-random component. As a consequence of that, it should not be possible to decipher it. There is nothing else stored locally than your master password in your security-settings file and it won't be ever prompted or asked again.
This master password is used to cipher and decipher passwords in your settings file. It has the same value as an user-introduced password, but it is almost impossible to deduce it.
Then:
  1. There is nothing else stored locally than your master password in your security-settings file and it won't be ever prompted or asked again. All the safety resides in the safety of the security-settings file.
  2. The master password is not really important and you can forget immediately. You can use whatever you want.
I don't like this approach to protect my password and I would like having a real password cyphering mechanism with a real master password not stored. Public-private key with password strategies seems to be better.

ant-run
https://maven.apache.org/guides/mini/guide-using-ant.html
  1. <plugin>
  2. <artifactId>maven-antrun-plugin</artifactId>
  3. <version>1.7</version>
  4. <executions>
  5. <execution>
  6. <phase>generate-sources</phase>
  7. <configuration>
  8. <tasks>
  9. <exec
  10. dir="${project.basedir}"
  11. executable="${project.basedir}/src/main/sh/do-something.sh"
  12. failonerror="true">
  13. <arg line="arg1 arg2 arg3 arg4" />
  14. </exec>
  15. </tasks>
  16. </configuration>
  17. <goals>
  18. <goal>run</goal>
  19. </goals>
  20. </execution>
  21. </executions>
  22. </plugin>
copy-rename
http://stackoverflow.com/questions/3998596/renaming-resources-in-maven
https://coderplus.github.io/copy-rename-maven-plugin/usage.html
      <plugin>
        <groupId>com.coderplus.maven.plugins</groupId>
        <artifactId>copy-rename-maven-plugin</artifactId>
        <version>1.0</version>
        <executions>
          <execution>
            <id>copy-file</id>
            <phase>generate-sources</phase>
            <goals>
              <goal>copy</goal>
            </goals>
            <configuration>
              <sourceFile>src/someDirectory/test.environment.properties</sourceFile>
              <destinationFile>target/someDir/environment.properties</destinationFile>
            </configuration>
          </execution>
        </executions>
      </plugin>

            <configuration>
              <fileSets>
                <fileSet>
                  <sourceFile>src/someDirectory/test.environment.properties</sourceFile>
                  <destinationFile>target/someDir/environment.properties</destinationFile>
                </fileSet>
                <fileSet>
                  <sourceFile>src/someDirectory/test.logback.xml</sourceFile>
                  <destinationFile>target/someDir/logback.xml</destinationFile>
                </fileSet>                
              </fileSets>
            </configuration>

http://apple.stackexchange.com/questions/89019/how-to-enable-maven-autocomplete-on-mac-os-x-command-line
Maven doesn't ship with an auto-complete script, but there's a project on GitHub called Maven Bash Completetion.
Installation if you use Homebrew:
  1. brew tap homebrew/completions
  2. brew install maven-completion
Otherwise, use this command to download the latest script (to your home directory as ~/.maven-completion.bash):
wget https://raw.github.com/juven/maven-bash-completion/master/bash_completion.bash \
    -O ~/.maven-completion.bash
Then add this to your ~/.bash_profile:
if [ -f ~/.maven-completion.bash ]; then
  . ~/.maven-completion.bash
fi
https://github.com/juven/maven-bash-completion
  1. Download bash_completion.bash and save it to any place you want, like ~/.maven_bash_completion.bash.
  2. Make your login shell load the script automatically by adding the line below to ~/.bash_profile (note the space after dot):
    . ~/.maven_bash_completion.bash
Example install as a one-line command line call for Debian and other distro:
sudo wget https://raw.github.com/dimaj/maven-bash-completion/master/bash_completion.bash --output-document /etc/bash_completion.d/mvn

http://stackoverflow.com/questions/7456006/maven-packaging-without-test-skip-tests
You can also skip the tests via the command line by executing the following command:
mvn install -DskipTests
If you absolutely must, you can also use the maven.test.skip property to skip compiling the tests. maven.test.skip is honored by Surefire, Failsafe and the Compiler Plugin.
mvn install -Dmaven.test.skip=true
Scope
http://stackoverflow.com/questions/6646959/difference-between-maven-scope-compile-and-provided-for-jar-packaging
  • provided
This is much like compile, but indicates you expect the JDK or a container to provide the dependency at runtime. For example, when building a web application for the Java Enterprise Edition, you would set the dependency on the Servlet API and related Java EE APIs to scope provided because the web container provides those classes. This scope is only available on the compilation and test classpath, and is not transitive.
Recap:
  • dependencies are not transitive (as you mentioned)
  • provided scope is only available on the compilation and test classpath, whereas compile scope is available in all classpaths.
  • provided dependencies are not packaged
https://robert-reiz.com/2011/10/19/uber-jar-with-maven/
https://maven.apache.org/plugins/maven-shade-plugin/examples/includes-excludes.html
  1. <groupId>org.apache.maven.plugins</groupId>
  2. <artifactId>maven-shade-plugin</artifactId>
  3. <version>2.4.3</version>
http://www.mkyong.com/maven/how-to-create-a-jar-file-with-maven/
https://maven.apache.org/plugins/maven-jar-plugin/usage.html
Since 'jar' is the default packaging type it is not required to set it in this case. 

http://stackoverflow.com/questions/10688344/in-eclipse-m2e-how-to-reference-workspace-project
The safest thing I found was to run mvn eclipse:clean from the command line then go back in to eclipse, refresh the project, "OK" the resulting problem dialog, and then go Maven > Update Project. This sorted it all out for me.
http://maven.apache.org/guides/mini/guide-attached-tests.html
Many times you may want to reuse the tests that you have created for a project in another. For example if you have written foo-core and it contains test code in the${basedir}/src/test/java it would be useful to package up those compiled tests in a JAR and deploy them for general reuse. 
http://stackoverflow.com/questions/174560/sharing-test-code-in-maven
     <plugin>
       <groupId>org.apache.maven.plugins</groupId>
       <artifactId>maven-jar-plugin</artifactId>
       <version>2.4</version>
       <executions>
         <execution>
           <goals>
             <goal>test-jar</goal>
           </goals>
         </execution>
       </executions>
     </plugin>
In order to use the attached test JAR that was created above you simply specify a dependency on the main artifact with a specified classifier of tests:
<project>
  ...
  <dependencies>
    <dependency>
      <groupId>com.myco.app</groupId>
      <artifactId>foo</artifactId>
      <version>1.0-SNAPSHOT</version>
      <type>test-jar</type>
      <scope>test</scope>
    </dependency>
  </dependencies>
  ...
</project> 

mvn help:evaluate
http://stackoverflow.com/questions/2877436/how-can-i-ask-maven-for-a-list-of-the-default-repositories
on the command line, execute
mvn help:evaluate
then, when prompted, enter
${project.repositories}
You can output the effective pom with the command
mvn help:effective-pom
There the default repositories are listed.
mvn dependency:list-repositories
http://repo1.maven.org/maven2/
&lt;repositories&gt;
    &lt;repository&gt;
        &lt;id&gt;the-real-central&lt;/id&gt;
        &lt;url&gt;http://repo1.maven.org/maven2&lt;/url&gt;
        &lt;releases&gt;
            &lt;checksumPolicy&gt;fail&lt;/checksumPolicy&gt;
            &lt;enabled&gt;true&lt;/enabled&gt;
        &lt;/releases&gt;
        &lt;snapshots&gt;
            &lt;checksumPolicy&gt;fail&lt;/checksumPolicy&gt;
            &lt;updatePolicy&gt;never&lt;/updatePolicy&gt;
        &lt;/snapshots&gt;
    &lt;/repository&gt;
&lt;/repositories&gt;
&lt;pluginRepositories&gt;
    &lt;pluginRepository&gt;
        &lt;id&gt;the-real-central&lt;/id&gt;
        &lt;url&gt;http://repo1.maven.org/maven2&lt;/url&gt;
        &lt;releases&gt;
            &lt;checksumPolicy&gt;fail&lt;/checksumPolicy&gt;
            &lt;enabled&gt;true&lt;/enabled&gt;
        &lt;/releases&gt;
        &lt;snapshots&gt;
            &lt;checksumPolicy&gt;fail&lt;/checksumPolicy&gt;
            &lt;updatePolicy&gt;never&lt;/updatePolicy&gt;
        &lt;/snapshots&gt;
    &lt;/pluginRepository&gt;
&lt;/pluginRepositories&gt;
Maven offline mode: -o
https://maven.apache.org/plugins/maven-dependency-plugin/list-repositories-mojo.html
dependency:list-repositories
Goal that resolves all project dependencies and then lists the repositories used by the build and by the transitive dependencies


To explain this a bit more, maven checks for the needed artifacts in the repositories configured. In most cases, the artifacts exist in the "default" repositories, and no extra repositories are needed.
On the other hand, let's say you have built your own maven artifact, and host your own maven repository. You publish the artifact to that repository. Now, if other users want to use it, they would have to do a configuration similar to the one above.
And by the way, -U forces updates, which is not needed unless you really want to force maven to download/re-download the dependencies.

mvn clean install -e -X -U
http://stackoverflow.com/questions/4650460/maven-could-not-resolve-dependencies-artifacts-could-not-be-resolved
You may also want to add the maven central repository for these artifacts in case they are not available in the specified repositories.
  <repository>
   <id>maven2</id>
   <url>http://repo1.maven.org/maven2</url>
  </repository>
http://stackoverflow.com/questions/10757089/maven-skip-site-reporting-for-module
You can also ignore report generation on the command line:
mvn -DgenerateReports=false package

You can also ignore report generation with:

mvn -Dmaven.site.skip=true clean install for example

Maven lifecycle
https://maven.apache.org/ref/3.3.3/maven-core/lifecycles.html
https://maven.apache.org/guides/introduction/introduction-to-the-lifecycle.html
For example, the default lifecycle comprises of the following phases (for a complete list of the lifecycle phases, refer to the Lifecycle Reference):
  • validate - validate the project is correct and all necessary information is available
  • compile - compile the source code of the project
  • test - test the compiled source code using a suitable unit testing framework. These tests should not require the code be packaged or deployed
  • package - take the compiled code and package it in its distributable format, such as a JAR.
  • integration-test - process and deploy the package if necessary into an environment where integration tests can be run
  • verify - run any checks to verify the package is valid and meets quality criteria
  • install - install the package into the local repository, for use as a dependency in other projects locally
  • deploy - done in an integration or release environment, copies the final package to the remote repository for sharing with other developers and projects.
https://maven.apache.org/ref/3.3.3/maven-core/lifecycles.html


default lifecycle is defined without any associated plugin. Plugin bindings for this lifecycle are defined separately for every packaging:
<phases>
  <phase>validate</phase>
  <phase>initialize</phase>
  <phase>generate-sources</phase>
  <phase>process-sources</phase>
  <phase>generate-resources</phase>
  <phase>process-resources</phase>
  <phase>compile</phase>
  <phase>process-classes</phase>
  <phase>generate-test-sources</phase>
  <phase>process-test-sources</phase>
  <phase>generate-test-resources</phase>
  <phase>process-test-resources</phase>
  <phase>test-compile</phase>
  <phase>process-test-classes</phase>
  <phase>test</phase>
  <phase>prepare-package</phase>
  <phase>package</phase>
  <phase>pre-integration-test</phase>
  <phase>integration-test</phase>
  <phase>post-integration-test</phase>
  <phase>verify</phase>
  <phase>install</phase>
  <phase>deploy</phase>
</phases>

How to create multiple modules projects
If you are working with the eclipse IDE you should use the m2eclipse plug-in. This is one of the easiest way to create multi-module projects. You can add a module to every maven project by creating a 'Maven Module-Project' within eclipse. When doing this you have the possibility to select a parent project. The plug-in does everything, means it copies the new module to parent module and modifies the pom.xml file.
mvn archetype:create has been deprecated in favor of mvn archetype:generate, so just the name changed. - mvn archetype:generate
http://websystique.com/maven/creating-maven-multi-module-project-with-eclipse/
mvn archetype:generate -DgroupId=com.websystique.multimodule -DartifactId=parent-project
cd parent-project
mvn archetype:generate -DgroupId=com.websystique.multimodule  -DartifactId=model-lib
mvn archetype:generate -DgroupId=com.websystique.multimodule  -DartifactId=webapp1
mvn archetype:generate -DgroupId=com.websystique.multimodule  -DartifactId=webapp2


https://benkiew.wordpress.com/2015/01/20/maven-force-the-exclusion-of-dependencies/
Once you got a candidate you can start finding all the possible sources of the dependency.
1
mvn dependency:tree -Dverbose -Dincludes=log4j:log4j
will show you the dependency-tree, but only the relevant excerpt. Using this information you can now add your exclusions to the affected pom.xml files.
Exclusions are configured via the exclusion-tag [1], which excludes specific transitive dependencies


After that you can make sure the faulty dependency versions will never ever be included again. This can be done using the maven-enforcer-plugin [2]

The Enforcer plugin provides goals to control certain environmental constraints such as Maven version, JDK version and OS family along with many more standard rules and user created rules.
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-enforcer-plugin</artifactId>
            <version>1.3.1</version>
            <executions>
                <execution>
                    <id>enforce-version</id>
                    <goals>
                        <goal>enforce</goal>
                    </goals>
                    <configuration>
                        <rules>
                            <bannedDependencies>
                                <excludes>
                                    <!-- exclude all versions lower than 1.2.17-->                                   
                                    <exclude>log4j:log4j:[0.0,1.2.17)</exclude>
                                </excludes>
                            </bannedDependencies>
                        </rules>
                    </configuration>
                </execution>
            </executions>
        </plugin>
查找maven工程中循环依赖的脚本
mvn dependency:tree -Dverbose | awk -F'- ' '{if(index($2,"maven-dependency-plugin")>0){indent=0;}else{indent=length($1);}stack[indent]=$2;if(index($0,"for cycle")>0){print "****found cycle****";for(i=0;i<=indent;i++){if(stack[i]!=null){print "->"stack[i]}}}}'

How do you clear Apache Maven's cache?
mvn dependency:purge-local-repository
How to simply download a JAR using Maven?
mvn dependency:get -DremoteRepositories=http://repo1.maven.org/maven2/ \
                   -DgroupId=junit -DartifactId=junit -Dversion=4.8.2 \
                   -Dtransitive=false
https://maven.apache.org/plugins/maven-jar-plugin/examples/create-test-jar.html
When you want to create a jar containing test-classes, you would probably want to reuse those classes. There are two ways to solve this:
  • Create an attached jar with the test-classes from the current project and loose its transitive test-scoped dependencies.
  • Create a separate project with the test-classes.
http://stackoverflow.com/questions/11668583/maven-create-directory-structure-from-pom-xml
Not to sound condescending, but:

mkdir -p src/main/java
mkdir -p src/main/resources
mkdir -p src/test/java
mkdir -p src/test/resources

http://www.avajava.com/tutorials/lessons/how-do-i-add-a-project-as-a-dependency-of-another-project.html

http://www.mojohaus.org/versions-maven-plugin/display-dependency-updates-mojo.html
org.codehaus.mojo:versions-maven-plugin:2.2:display-dependency-updates
Displays all dependencies that have newer versions available. This will show a list of all updated dependencies. There is a similar command to show a list of all the updated plugins.

Maven Lifecycle
https://maven.apache.org/guides/introduction/introduction-to-the-lifecycle.html
  • validate - validate the project is correct and all necessary information is available
  • compile - compile the source code of the project
  • test - test the compiled source code using a suitable unit testing framework. These tests should not require the code be packaged or deployed
  • package - take the compiled code and package it in its distributable format, such as a JAR.
  • integration-test - process and deploy the package if necessary into an environment where integration tests can be run
  • verify - run any checks to verify the package is valid and meets quality criteria
  • install - install the package into the local repository, for use as a dependency in other projects locally
  • deploy - done in an integration or release environment, copies the final package to the remote repository for sharing with other developers and projects.
Change build jar/war name:
<build>
    <finalName>${rp.build.warname}-somearbitraryname</finalName>
    <!-- ... -->
</build>
To exclude any file from a jar / target directory you can use the <excludes> tag in your pom.xml file.
<build>
    <resources>
        <resource>
            <directory>src/main/resources</directory>
            <excludes>
                <exclude>*.properties</exclude>
            </excludes>
            <filtering>false</filtering>
        </resource>
    </resources>
</build>
How to solve “Plugin execution not covered by lifecycle configuration” for Spring Data Maven Builds
In my case of a similar problem, instead of using Andrew's suggestion for the fix, it worked simply after I introduced <pluginManagement> tag to the pom.xml in question. Looks like that error is due to a missing <pluginManagement> tag. So, in order to avoid the exceptions in Eclipse, looks like one needs to simply enclose all the plugin tags inside a <pluginManagement> tag, like so:
<build>
    <pluginManagement>
        <plugins>
            <plugin> ... </plugin>
            <plugin> ... </plugin>
                  ....
        </plugins>
    </pluginManagement>
</build>
Once this structure is in place, the error goes away.
You still need to add
<plugins>
    <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-dependency-plugin</artifactId>
    </plugin>
</plugins>
in your build, because pluginManagement is only a way to share the same plugin configuration across all your project modules.
From Maven documentation:
pluginManagement: is an element that is seen along side plugins. Plugin Management contains plugin elements in much the same way, except that rather than configuring plugin information for this particular project build, it is intended to configure project builds that inherit from this one. However, this only configures plugins that are actually referenced within the plugins element in the children. The children have every right to override pluginManagement definitions.
By default, plugin configuration should be propagated to child POMs, so to break the inheritance, you could uses the <inherited> tag:
http://i-proving.com/2009/01/13/managing-your-plugins-as-distinct-from-pluginmanagement/
the <pluginManagement> section contains:
Default plugin information to be made available for reference by projects derived from this one. This plugin configuration will not be resolved or bound to the lifecycle unless referenced. Any local configuration for a given plugin will override the plugin’s entire definition here.
M2E plugin execution not covered
https://www.eclipse.org/m2e/documentation/m2e-execution-not-covered.html
M2Eclipse 1.0 requires explicit instructions what to do with all Maven plugins bound to “interesting” phases of a project build lifecycle. We call these instructions “project build lifecycle mapping” because they define how m2e maps information from project pom.xml file to Eclipse workspace project configuration and behaviour during Eclipse workspace build.

There are three basic actions that M2Eclipse can be instructed to do with a plugin execution – ignore, execute and delegate to a project configurator.

Delegate to a Project Configurator (recommended)
In most cases a configurator mapping will be used by M2Eclipse extension developers

Execute Plugin Goal
The execute option tells m2e to execute the action as part of Eclipse workspace full or incremental build.

<action>
<execute>
 <runOnIncremental>false</runOnIncremental>
</execute >
</action>
HINT: Use quick fix to create “ignore” mapping, then replace <ignore/> action with <execute/>. M2Eclipse 1.3 and newer assume safer runOnIncremental=false by default. It is recommended to always specific desired runOnIncremental value explicitly in lifecycle mapping configuration.

What is this web resources folder?
target/m2e-wtp/web-resources/ is a folder containing automatically generated resources, that need to be deployed on the application server.

Force maven update
mvn clean install -U
-U means force update of dependencies.
Mastering Apache Maven 3
Defining a parent module
Examples:
https://svn.wso2.org/repos/wso2/carbon/platform/trunk/

Some just keep the parent POM file under the root directory (not under the parent module).
http://svn.apache.org/repos/asf/hbase/trunk/pom.xml
However, the first one is much preferred. With the first approach, the parent POM file only defines the shared resources across different Maven modules in the project, while there is another POM file at the root of the project, which defines all the modules to be included in the project build.

you need to introduce the dependencyManagement configuration element in the parent POM so that it will be inherited by all the other child modules.
Define pluginManagement in parent pom.xml.

POM properties:
Built-in properties
Project properties
Local settings
Environment variables
Java system properties
Custom properties
${project.version}, project.baseUri/name
  <systemPath>${project.basedir}/lib/axis2-1.6.jar</systemPath>
${settings.localRepository}
${env.M2_HOME}, ${env.java_home}

Avoiding repetitive groupId and version tags and inherit from the parent POM
Avoid using digits or special characters (that is, org.wso2.carbon.identity-core).
Do not try to group two words into a single word by camel casing (that is, org.wso2.carbon.identityCore).
–Dproduct=is
<activation>
  <property>
    <name>!product</name>
  </property>
</activation>
<activation>
  <property>
    <name>product</name>
    <value>is</value>
  </property>
</activation>
Apache Maven Cookbook
dependencyManagement takes precedence over dependency mediation and ensures that dependency mediation does not pick a version over the one specified in dependencyManagement.

It should be noted that dependencies on different versions are error prone and dependencyManagement cannot always save them from library version incompatibilities.

Performing multi-module plugin management
If a plugin is used as part of the build lifecycle, then its configuration in the pluginManagement section will take effect, even if not explicitly defined by the child.
  <pluginManagement>
      <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-compiler-plugin</artifactId>
            <version>3.2</version>
            <configuration>
              <source>1.8</source>
              <target>1.8</target>
            </configuration>
        </plugin>
      <plugin>
</pluginManagement>
<inherited>false</inherited>
Selectively building modules
mvn –P dev clean test
<profiles>
    <profile>
        <id>dev</id>
        <modules>
            <module>common-one</module>
            <module>dev-two</module>
        </modules>
    </profile>
</profiles>
http://greyfocus.com/2015/06/activebydefault-maven-other-profiles/
<profiles>
  <profile>
    <id>default</id>
    <activation>
      <property>
        <name>!skipDefault</name>
      </property>
    </activation>
  </profile>
</profiles>
http://stackoverflow.com/questions/9279852/ignore-a-module-during-maven-test-build-for-multi-module-maven-project
<build>
    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-surefire-plugin</artifactId>
            <version>2.12</version>
            <configuration>
                <skipTests>${skip.foo.module.tests}</skipTests>
            </configuration>
        </plugin>
    </plugins>
</build>
... and delegate the true/false value of the skipTests tag to a maven property, activated by a dedicated profile :
<properties>
    <skip.foo.module.tests>false</skip.foo.module.tests>
</properties>

<profiles>
    <profile>
        <id>SKIP_FOO_MODULE_TESTS</id>
        <properties>
            <skip.foo.module.tests>true</skip.foo.module.tests>
        </properties>
    </profile>
</profiles>
So that you could deactivate the tests in Foo module with the command line :
mvn clean test -P SKIP_FOO_MODULE_TESTS

Reporting for multi-module projects
Add the following command to the reporting section of the parent pom for checkstyle:
    <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-checkstyle-plugin</artifactId>
        <version>2.13</version>
        <reportSets>
          <reportSet>
            <id>aggregate</id>
            <inherited>false</inherited>
            <reports>
              <report>checkstyle-aggregate</report>
            </reports>
          </reportSet>
        </reportSets>
      </plugin>
<distributionManagement>
    <site>
      <id>packt</id>
      <url>file:///C:/fullsite</url>
    </site>
</distributionManagement>
mvn site:stage –DstagingDirectory=C:/fullsite

Reporting
http://kohsuke.org/2011/08/23/my-epic-battle-with-findbugs-maven-plugin-and-how-i-utterly-lost/

https://maven.apache.org/plugins-archives/maven-site-plugin-3.2/examples/multimodule.html
http://stackoverflow.com/questions/10848715/multi-module-pom-creating-a-site-that-works
Running mvn site on a top level project, maven will build all sites for every module defined in the modules section of the pom individually. Note that each site is generated in each individual project's target location. As a result, relative links between different modules will NOT work. They will however work when you deploy or stage the site.

site:deploy does the same thing as site:stage but uses the url defined in the <distributionManagement> element of the pom as deployment location. This is usually a remote url, but both scp and file protocols are supported.

Finally, site:stage-deploy does the same thing as site:deploy but uses the stagingDirectory parameter as deployment location. This can be used to deploy the site to a remote staging area (site:stage is always local).

http://stackoverflow.com/questions/3908013/maven-how-to-change-path-to-target-directory-from-command-line

You should use profiles.
<profiles>
    <profile>
        <id>otherOutputDir</id>
        <build>
            <directory>yourDirectory</directory>
        </build>
    </profile>
</profiles>
And start maven with your profile
mvn compile -PotherOutputDir
If you really want to define your directory from the command line you could do something like this (NOT recommended at all) :
<properties>
    <buildDirectory>${project.basedir}/target</buildDirectory>
</properties>

<build>
    <directory>${buildDirectory}</directory>
</build>
And compile like this :
mvn compile -DbuildDirectory=test
That's because you can't change the target directory by using -Dproject.build.directory
http://grep.codeconsult.ch/2010/07/08/list-all-your-maven-dependencies/
mvn dependency:resolve

# then list them with -o to keep noise low,
# remove extra information and duplicates
mvn -o dependency:list \
| grep ":.*:.*:.*" \
| cut -d] -f2- \
| sed 's/:[a-z]*$//g' \
| sort -u 
so it’s also useful to detect multiple versions of the same dependency in a multi-module project.

https://bugs.eclipse.org/bugs/show_bug.cgi?id=396589
Classpath container entries order is determined by pom.xml and cannot be changed without (potentially) breaking compilation, for example. What you want is a UI option to display classpath container entries alphabetically, which is not currently possible in Package Explorer due to JDT limitation.

It is possible to see maven dependencies in alphabetical order and search for dependencies using Dependency Hierarchy tab of pom.xml editor.

Maven对重复依赖的解决方案

Maven对重复依赖的解决方案

当一个项目中出现重复的依赖包时,maven 2.0.9之后的版本会用如下的规则来决定使用哪一个版本的包:

最短路径原则

比如有如下两个依赖关系:
A -> B -> C -> D(V1)
F -> G -> D(V2)
这个时候项目中就出现了两个版本的D,这时maven会采用最短路径原则,选择V2版本的D,因为V1版本的D是由A包间接依赖的,整个依赖路径长度为3,而V2版本的D是由F包间接依赖的,整个依赖路径长度为2。

声明优先原则

假设有如下两个依赖关系:
A -> B -> D(V1)
F -> G -> D(V2)
这个时候因为两个版本的D的依赖路径都是一样长,最短路径原则就失效了。这个时候Maven的解决方案是:按照依赖包在pom.xml中声明的先后顺序,优先选择先声明的包

Labels

Review (572) System Design (334) System Design - Review (198) Java (189) Coding (75) Interview-System Design (65) Interview (63) Book Notes (59) Coding - Review (59) to-do (45) Linux (43) Knowledge (39) Interview-Java (35) Knowledge - Review (32) Database (31) Design Patterns (31) Big Data (29) Product Architecture (28) MultiThread (27) Soft Skills (27) Concurrency (26) Cracking Code Interview (26) Miscs (25) Distributed (24) OOD Design (24) Google (23) Career (22) Interview - Review (21) Java - Code (21) Operating System (21) Interview Q&A (20) System Design - Practice (20) Tips (19) Algorithm (17) Company - Facebook (17) Security (17) How to Ace Interview (16) Brain Teaser (14) Linux - Shell (14) Redis (14) Testing (14) Tools (14) Code Quality (13) Search (13) Spark (13) Spring (13) Company - LinkedIn (12) How to (12) Interview-Database (12) Interview-Operating System (12) Solr (12) Architecture Principles (11) Resource (10) Amazon (9) Cache (9) Git (9) Interview - MultiThread (9) Scalability (9) Trouble Shooting (9) Web Dev (9) Architecture Model (8) Better Programmer (8) Cassandra (8) Company - Uber (8) Java67 (8) Math (8) OO Design principles (8) SOLID (8) Design (7) Interview Corner (7) JVM (7) Java Basics (7) Kafka (7) Mac (7) Machine Learning (7) NoSQL (7) C++ (6) Chrome (6) File System (6) Highscalability (6) How to Better (6) Network (6) Restful (6) CareerCup (5) Code Review (5) Hash (5) How to Interview (5) JDK Source Code (5) JavaScript (5) Leetcode (5) Must Known (5) Python (5)

Popular Posts