title: How to cache maven dependencies in Docker
body: <p>I'm working on a project with ~200MB dependencies and i'd like to avoid useless uploads due to my limited bandwidth. </p>
  
  <p>When I push my Dockerfile (i'll attach it in a moment), I always have a ~200MB upload even if I didn't touch the pom.xml:</p>
  
  <pre><code>FROM maven:3.6.0-jdk-8-slim
  
  WORKDIR /app
  
  ADD pom.xml /app
  
  RUN mvn verify clean --fail-never
  
  COPY ./src /app/src
  
  RUN mvn package
  
  ENV CONFIG_FOLDER=/app/config
  ENV DATA_FOLDER=/app/data
  ENV GOLDENS_FOLDER=/app/goldens
  ENV DEBUG_FOLDER=/app/debug
  
  WORKDIR target
  
  CMD ["java","-jar","-Dlogs=/app/logs", "myProject.jar"]
  </code></pre>
  
  <p>This Dockerfile should make a 200MB fatJAR including all the dependencies, that's why the ~200MB upload that occurs everytime. What i would like to achieve is building a Layer with all the dependencies and "tell" to the packaging phase to not include the dependencies JARs into the fatJAR but to search for them inside a given directory.</p>
  
  <p>I was wondering to build a script that executes <code>mvn dependency:copy-dependencies</code> before the building process and then copying the directory to the container; then building a "non-fat"JAR that has all those dependencies only linked and not actually copied into it.</p>
  
  <p>Is this possible?</p>
  
  <p><strong>EDIT:</strong> 
  I discovered that the Maven Local Repository of the container is located under <code>/root/.m2</code>. So I ended making a very simple script like this:</p>
  
  <p><em>BuildDocker.sh</em></p>
  
  <pre><code>mvn verify -clean --fail-never
  mv ~/.m2 ~/git/myProjectRepo/.m2
  
  sudo docker build -t myName/myProject:"$1"
  </code></pre>
  
  <p>And edited <em>Dockerfile</em> like:</p>
  
  <pre><code># Use an official Python runtime as a parent image
  FROM maven:3.6.0-jdk-8-slim
  
  # Copy my Mavne Local Repository into the container thus creating a new layer
  COPY ./.m2 /root/.m2
  
  # Set the working directory to /app
  WORKDIR /app
  
  # Copy the pom.xml
  ADD pom.xml /app
  
  # Resolve and Download all dependencies: this will be done only if the pom.xml has any changes
  RUN mvn verify clean --fail-never
  
  # Copy source code and configs 
  COPY ./src /app/src
  
  # create a ThinJAR
  RUN mvn package
  
  
  # Run the jar
  ...
  </code></pre>
  
  <p>After the building process i stated that <code>/root/.m2</code> has all the directories I but as soon as i launch the JAR i get:</p>
  
  <pre><code>Exception in thread "main" java.lang.NoClassDefFoundError: org/apache/log4j/Priority
      at myProject.ThreeMeans.calculate(ThreeMeans.java:17)
      at myProject.ClusteringStartup.main(ClusteringStartup.java:7)
  Caused by: java.lang.ClassNotFoundException: org.apache.log4j.Priority
      at java.net.URLClassLoader.findClass(URLClassLoader.java:382)
      at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
      at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:349)
      at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
      ... 2 more
  </code></pre>
  
  <p>Maybe i shouldn't run it through <code>java -jar</code>?</p>