Необязательные зависимости Gradle для библиотек Maven

Я работаю над библиотекой Android и хотел бы использовать зависимость, только если проект, использующий мою библиотеку, также включает эту зависимость. Подобно тому, что Пикассо делает с OkHttp.

Я уже позаботился об этом в основном коде, проверив наличие ClassNotFoundExceptions, но он по-прежнему включает зависимости при развертывании его в Maven Central. Как мне сгенерировать что-то вроде Maven's <optional>true</optional> тег?

Я использую gradle-mvn-push для развертывания моих артефактов через Gradle.

3 ответа

Решение

Голосуйте за GRADLE-1749.

В то же время вы можете использовать pom.withXml подход для изменения сгенерированного файла POM, например, чтобы добавить <optional> теги или изменения <scope>ценности:

apply plugin: 'java'
apply plugin: 'maven-publish'

configurations {
  optional
  compile.extendsFrom optional
}

dependencies {
  compile 'com.some.group:artifact:1.0';
  optional 'com.another.group:optional-artifact:1.0'
}

publishing {
  publications {
    maven( MavenPublication ) {
      from components.java

      pom.withXml {
        asNode().dependencies.dependency.findAll { xmlDep ->
          // mark optional dependencies
          if ( project.configurations.optional.allDependencies.findAll { dep ->
            xmlDep.groupId.text() == dep.group && xmlDep.artifactId.text() == dep.name
          } ) {
            def xmlOptional = xmlDep.optional[ 0 ];
            if ( !xmlOptional ) {
              xmlOptional = xmlDep.appendNode( 'optional' )
            }
            xmlOptional.value = 'true';
          }

          // fix maven-publish issue when all maven dependencies are placed into runtime scope
          if ( project.configurations.compile.allDependencies.findAll { dep ->
            xmlDep.groupId.text() == dep.group && xmlDep.artifactId.text() == dep.name
          } ) {
            def xmlScope = xmlDep.scope[ 0 ];
            if ( !xmlScope ) {
              xmlScope = xmlDep.appendNode( 'scope' )
            }
            xmlScope.value = 'compile';
          }
        }
      }
    }
  }
}

Плагин Nebula Extra Configurations Gradle, кажется, предоставляет дополнительные возможности.

Вы бы использовали это так:

apply plugin: 'java'
apply plugin: 'nebula.optional-base'

repositories {
    mavenCentral()
}

dependencies {
    compile 'org.apache.commons:commons-lang3:3.3.2', optional
    compile group: 'log4j', name: 'log4j', version: '1.2.17', optional
}

Согласно этому блогу , зависимости только для компиляции относятся к ряду вариантов использования, в том числе:

  • Зависимости, необходимые во время компиляции, но требуемые во время выполнения только при использовании определенных функций, также называемых необязательными зависимостями;
  • Зависимости, необходимые во время компиляции, но никогда не требуемые во время выполнения, такие как аннотации только для исходного кода или обработчики аннотаций;
  • Зависимости, API которых требуется во время компиляции, но реализация которых должна быть предоставлена ​​потребляющей библиотекой, приложением или средой выполнения.

Поэтому просто используйте compileOnly для объявления необязательной зависимости.

Другие вопросы по тегам