Maven-embedder 3.1.1

Hi!

I’m trying to use maven-embedder 3.1.1 with Gradle 1.9. Starting with version 3.1.0 Maven uses slf4j for logging. maven-embedder tries to configure the log level and then runs into the following error:

java.lang.NoClassDefFoundError: ch/qos/logback/classic/Level

I was able to reproduce the issue with the following minimal build script:

import org.slf4j.LoggerFactory
import ch.qos.logback.classic.LoggerContext
  task testLog << {
    //this is exactly what maven-embedder is doing
    //see org.apache.maven.cli.logging.impl.LogbackConfiguration
    def lf = (LoggerContext)LoggerFactory.getILoggerFactory()
    println(lf)
}

This script does not work, because slf4j is in the classpath but logback is not. I tried to add logback to the classpath, but this failed as well:

buildscript {
    repositories {
        mavenCentral()
    }
      dependencies {
        classpath 'ch.qos.logback:logback-classic:1.0.9'
    }
}
  import org.slf4j.LoggerFactory
import ch.qos.logback.classic.LoggerContext
  task testLog << {
    def lf = (LoggerContext)LoggerFactory.getILoggerFactory()
    println(lf)
}

I received the following error:

> Cannot cast object 'ch.qos.logback.classic.LoggerContext[default]' with class 'ch.qos.logback.classic.LoggerContext' to class 'ch.qos.logback.classic.LoggerContext'

Is there a solution for this?

Thanks, Michel

Michel, have you managed to workaround this issue?

Finally I found how to call maven using Ant which is integrated into gradle.

The idea is described at http://stackoverflow.com/questions/4120575/how-to-use-the-maven-ant-task-from-gradle

For me the following code works:

configurations {
 mavenAntTasks
}
  dependencies {
 mavenAntTasks 'org.apache.maven:maven-ant-tasks:2.1.3'
}
  task runMvn() << {
 ant.typedef(resource:'org/apache/maven/artifact/ant/antlib.xml',
   classpath: configurations.mavenAntTasks.asPath)
 ant.mvn(mavenVersion:'3.1.1', pom:file('pom.xml').toString(), failonerror:true) {
   arg(value:'package')
 }
}

The drawback is only missing output to console from maven build.

Nice solution, but doesn’t this fork another instance of Maven? What I wanted to do is use maven-embedder to make things faster and to save some resources.

I finally came up with the following solution which works at least in my setup. I’m using maven-embedder in my ‘buildSrc/build.gradle’:

dependencies {

compile ‘org.apache.maven:maven-embedder:3.1.1’

compile ‘org.apache.maven.wagon:wagon-http-lightweight:2.4’

compile ‘org.eclipse.aether:aether-connector-wagon:0.9.0.M2’

}

In order to override the Maven’s logging configuration I had to add a file named ‘buildSrc/src/main/resources/META-INF/maven/slf4j-configuration.properties’ with the following contents:

ch.qos.logback.classic.LoggerContext DummyLogbackConfiguration

Of course I had to implement this new ‘DummyLogbackConfiguration’ in ‘buildSrc/src/main/groovy/DummyLogbackConfiguration.groovy’.

import org.apache.maven.cli.logging.BaseSlf4jConfiguration
import org.apache.maven.cli.logging.Slf4jConfiguration.Level
    public class DummyLogbackConfiguration extends BaseSlf4jConfiguration {
    @Override
    public void setRootLoggerLevel(Level level) {
        // do not change Gradle's log level
    }
          @Override
    public void activate() {
        // no op
    }
}

I hope this helps. If you have questions, don’t hesitate to ask.

Cheers, Michel

but doesn’t this fork another instance of Maven?

Michel, as Ant’s Mvn task is inherited from Ant’s Java task which allows manage forking with parameter ‘fork’, quite flexible.