Gradle maven-publish:如何将testCompile依赖项添加到生成的pom中?

时间:2015-03-02 15:17:24

标签: gradle pom.xml maven-publish

使用maven-publish进行发布时(我知道,孵化),compile依赖项会添加到生成POM(runtime范围内),但是testCompile依赖性被忽略。

如何将testCompile依赖项作为test范围获取到生成的POM中?

3 个答案:

答案 0 :(得分:1)

POM仅在发布工件时使用;它会随着工件一起上传到Maven仓库。因此,POM只需要运行时依赖性。

Gradle执行独立于部署插件的测试,因此它不使用POM文件。

假设您正在使用Java插件,它会添加test源集。这反过来又创建了testCompile任务。

现在,如果不另行配置,Gradle会假定您的运行时依赖项与编译时依赖项相同。但是,它只考虑main源集。这就是你POM不包含test依赖关系的原因。

因此,总而言之,配置与以下类似的测试依赖项。然后,只要知道发布的工件不包含您的测试代码或其依赖项,就快乐。

dependencies {
    testCompile 'org.springframework:spring-test:4.+'
}

如果您遇到异常情况,即在无法访问测试源代码的计算机上执行测试,请更详细地说明您的要求。应该可以为测试代码设置单独的输出工件,因此可以发布它,但我仍然认为你不应该在与main源集相同的包(或POM)中发布它

答案 1 :(得分:1)

我用了几个小时来找到一个很好的方法来选择工件或出版物应该使用的构建配置,但没有运气。我的发现是,实现它的唯一方法是修改生成的POM XML,如下所示:

// build.gradle

publishing {
    repositories { /* skipped for brevity */ }

    publications {
        core(MavenPublication) {
            from components.java
            artifactId project.name

            artifact sourcesJar {
                classifier 'sources'
            }
        }

        generators(MavenPublication) {
            from components.java
            artifactId "${project.name}-generators"

            artifacts = [ generatorsJar ]
            artifact generatorsSourcesJar {
                classifier 'sources'
            }

            pom.withXml { pomXml -> replaceDependenciesWith('generatorsBase', pomXml) }
        }
    }
}

void replaceDependenciesWith(String configurationName, XmlProvider pomXml) {
    Node configurationDependencies = new Node(null, 'dependencies')
    project.configurations.getByName(configurationName).allDependencies.each { dep ->
        Node dependency = new Node(null, 'dependency')
        dependency.appendNode('groupId', dep.group)
        dependency.appendNode('artifactId', dep.name)
        dependency.appendNode('version', dep.version)
        dependency.appendNode('scope', 'compile')
        configurationDependencies.append(dependency)
    }
    pomXml.asNode().dependencies*.replaceNode(configurationDependencies)
}

以上在Gradle 3.3上工作

评论Groovy的类似XML构建器的语法

我也尝试使用Groovy的类似XML构建器的语法,但不幸的是错误的上下文附加到传递给replaceNode方法的闭包,因此它不起作用。内联时,它与publications {}闭包的上下文相同,而当提取到方法时,version dep.version没有按预期工作。)

// Does not work!
void replaceDependenciesWith(String configurationName, Node pomXmlNode) {
    pomXmlNode.dependencies*.replaceNode {
        dependencies {
            project.configurations.getByName(configurationName).allDependencies.each { dep ->
                dependency {
                    groupId dep.group
                    artifactId dep.name
                    version dep.version
                    scope 'compile'
                }
            }
        }
    }
}

答案 2 :(得分:0)

当我需要修改POM xml时,我无法使用groovy语言的任何功能。而且我必须像krzychu's answer一样直接依赖API。

否则,不会像我预期的那样应用xml闭包,构建失败并发出警告,或者未正确应用闭包,从而导致无效的pom。

但是最近,在仔细阅读groovy's closure文档之后,我注意到可以将resolutionStrategy应用于闭包,以帮助运行时找到正确的上下文(暗含了此)。

默认解决方案策略为Closure.OWNER_FIRST,这说明了为什么在某些试验中我对将闭包应用于publications时出错了。从他们的文档中,我尝试将策略设置为Closure.DELEGATE_FIRST,事实证明这可以按预期进行。

请注意,闭包必须应用于Node,因此.children()返回一个列表,.last()返回一个Node,您可以通过以下任一方法在其上添加另一个节点.plus(...)方法或其别名+

publishing {
    publications {
        core(MavenPublication) {
            pom.withXml {
                def dependenciesNode = 
                    asNode().dependencyManagement
                            .first()
                            .dependencies
                            .first()

                dependenciesNode.children().last().plus( {
                    resolveStrategy = Closure.DELEGATE_FIRST
                    dependency {
                        'groupId'('org.springframework.boot')
                        'artifactId'('spring-boot-dependencies')
                        'version'(rootProject.'spring-boot.version')
                        'type'('pom')
                        'scope'('import')
                    }
                })
            }
        }
    }
}

找到正确的语法就像在大海捞针中找到销钉,这里的一些链接(1)(2)(3)帮助我找到了resolutionStrategy