How execute annotation processing in gradle separatly from build task - java

I want to run QueryDsl Q-type generation in a separate task. I want that Q-type classes not to be created in a regular compileJava task, but the compiler sees the AnnotationProcessor in the classpath and creates them itself. I tried nulling the annotationProcessorPath, but then I couldn't restore its configuration in a separate task.
May be is it possible to exclude somehow dependencies of subtasks from the classpath?
compileJava {
options.annotationProcessorPath = null
}
tasks.register('generateQTypes'){
group 'build'
description 'Generate Q-Type classes with QueryDsl library'
dependencies {
annotationProcessor(
'com.querydsl:querydsl-apt:4.1.4:jpa',
'javax.persistence:javax.persistence-api:2.2',
'javax.annotation:javax.annotation-api:1.3.1')
}
compileJava {
options.annotationProcessorPath = classpath
}
}
What is the best way to solve this problem?Thanks in advance!

I made the following solution
class QTypeGenerator extends DefaultTask {
#TaskAction
addDependencies() {
project.dependencies {
annotationProcessor(
'com.querydsl:querydsl-apt:4.1.4:jpa',
'javax.persistence:javax.persistence-api:2.2',
'javax.annotation:javax.annotation-api:1.3.1')
}
}
}
tasks.register("generateQTypeClasses", QTypeGenerator) {
group('build')
description('Generate Q-type classes by queryDsl in build directory with default path')
finalizedBy('compileJava')
doLast {
println("Q-types classes will gererated and stored in ${compileJava.options.annotationProcessorGeneratedSourcesDirectory}")
}
}

Related

is it possible to force java module dependencies to use specify version [duplicate]

I have a distributes projects with different sub-projects and I want to accomplish the following:
(root)
client
module A
module B
module C
model
I want to put
protoc {
artifact = 'com.google.protobuf:protoc:3.5.0'
}
plugins {
grpc {
artifact = "io.grpc:protoc-gen-grpc-java:1.7.0"
}
}
generateProtoTasks {
all()*.plugins {
grpc {}
}
} }
dependencies {
compile "com.google.api.grpc:proto-google-common-protos:1.0.0"
compile "io.grpc:grpc-netty:1.7.0"
compile "io.grpc:grpc-protobuf:1.7.0"
compile "io.grpc:grpc-stub:1.7.0"
}
for module A, B and C.
For now I have the following in my root build.gradle
subprojects{
apply plugin: 'java'
sourceCompatibility = 1.8
group 'project'
version '0.0.1-SNAPSHOT'
jar {
manifest {
attributes 'Main-Class': "com.project.${project.name}.App"
}
doFirst {
from { configurations.runtime.collect { it.isDirectory() ? it : zipTree(it) } }
}
}
repositories {
mavenCentral()
mavenLocal()
}
dependencies {
testCompile 'junit:junit:4.12'
testCompile 'org.mockito:mockito-core:1.9.5'
}
}
So every sub-project use java plugin, and has the defines dependencies and jar task.
How can I only put the first block for some sub-projects ?
I tried using a variable like in Multi-project Builds - Gradle but I couldn't access it in subprojects block.
Thank you in advance. I'm really interested in using Gradle correctly and it's a bit hard to get into it outside of simple Android/Java projects. Feel free to include any documentations I should read :)
Edit:
Thank you. I wouldn't have posted here if I hadn't search before. Apparently I was missing the keyword "subset" who would have gave me the solution you linked.
A solution is described here: https://discuss.gradle.org/t/configure-only-subset-of-subprojects/5379/3
You can run configure() with a list of projects.
project.ext {
subprojectList = subprojects.findAll{
it.name == 'subprojectA' ||
it.name == 'subprojectB' ||
it.name == 'subprojectC'
}
}
configure(project.subprojectList) {
// insert your custom configuration code
}
or
configure([project(':a'), project(':b'), project(':c')]) {
// configuration
}

How to publish a shadow jar with an empty pom using gradle maven-publish plugin and Kotlin DSL?

The shadow plugin documentation has an example for groovy but I do not understand how to translate this to Kotlin.
Groovy example from https://imperceptiblethoughts.com/shadow/publishing :
publishing {
publications {
shadow(MavenPublication) { publication ->
project.shadow.component(publication)
}
}
}
My best attempt at the Kotlin version:
publishing {
publications {
create<MavenPublication>("pluginMaven") {
artifact(tasks["shadowJar"])
project.shadow.component(this)
}
}
}
With the above Kotlin version, shadowed dependencies show up in the resulting pom as runtime dependencies, which defies of purpose of shadowing.
The solution is
tasks {
shadowJar {
archiveClassifier.set("")
minimize()
}
}
Some background in this github issue.

How to find tasks of a certain type through all projects?

I have a multi-build Java project being built with Gradle.
To hide Illegal reflective access warnings I want to find JavaExec and Test tasks within several projects and provide the required JVM arguments. Rather than add these to each project, I want to apply this to all projects in the root build.gradle.
How do I find certain tasks of a certain type throughout all projects?
My intial attempt uses withType however I want to remove the duplication of repeating this for the JavaExec and Test task types. See below:
Attempt #1
allprojects {
repositories {
jcenter()
}
afterEvaluate {
project.tasks.withType(JavaExec) {
it.jvmArgs "--add-opens=java.base/java.lang=ALL-UNNAMED"
}
project.tasks.withType(Test) {
it.jvmArgs "--add-opens=java.base/java.lang=ALL-UNNAMED"
}
}
}
subprojects {
version = "0.0.1-SNAPSHOT"
}
Try this :
afterEvaluate {
[JavaExec, Test].each {
project.tasks.withType(it) {
it.jvmArgs "--add-opens=java.base/java.lang=ALL-UNNAMED"
}
}
}

How to call a task separately in gradle

My build.gradle file looks like below.
apply plugin: 'java'
repositories {
maven {
mavenCentral()
}
dependencies {
compile "commons-logging:commons-logging:1.0.4",
"commons-codec:commons-codec:1.3"
}
jar {
manifest{
attributes ("Product-Name" : project.name, "${manifestSectionName}")
attributes ("Product-Display-Name" : project.description, "${manifestSectionName}")
}
}
task build1 {
sourceSets {
main {
java {
srcDirs = ['src/java/com/abc/xyz/dir1']
}
}
}
buildDir = 'op'
jar{
archiveName = 'build1.jar'
}
}
task build2 {
sourceSets {
main {
java {
srcDirs = ['src/java/com/abc/xyz/dir2']
}
}
}
buildDir = 'op'
jar{
archiveName = 'build2.jar'
}
}
So now I want to call individual task to build individual jar, the way we invoke individual targets in Ant.
So when I am calling it like : gw clean build build2
its building build2.jar in correct way, but when I am running it like: gw clean build build1, its still building build2.jar only.
I am very new to gradle, so not sure about this.
Its still building build2.jar only, I am not sure why its happening .. can someone help me here?
Note that both tasks are independent of each other.
When configuring build1 and build2, you're configuring the unique, shared, main sourceSet and the unique, shared, jar task. Since build2 is configured after build1, it overrides the configuration set by build1.
What you want instead is two additional tasks in the build, which both create a jar with a different content:
task build1(type: Jar) {
dependsOn classes
archiveName = 'build1.jar'
from(sourceSets.main.output) {
include '**/package1/**/*'
}
}
task build2(type: Jar) {
dependsOn classes
archiveName = 'build2.jar'
from(sourceSets.main.output) {
include '**/package2/**/*'
}
}
But that looks to me like bad design. If you want to generate different jars, then you should probably have several subprojects, all using the java plugin and not needing any configuration.

Add provided dependency to test classpath using Gradle

I've provided dependency scope configured like below. My problem is, the provided dependencies are not visible during runtime in tests. How can I configure this to keep the dependencies provided but available on the test classpath?
apply plugin: 'java'
configurations {
provided
}
sourceSets {
main {
compileClasspath += configurations.provided
}
}
dependencies {
provided 'com.google.guava:guava:18.0'
provided 'org.apache.commons:commons-lang3:3.3.2'
// Tests
testCompile 'junit:junit:4.11'
testCompile 'org.assertj:assertj-core:1.7.0'
// Additional test compile dependencies
testCompile 'joda-time:joda-time:2.2'
}
One solution is to add the dependency like the joda-time library with testCompile scope, but I don't want to duplicate any entries. I'm sure it can be achieved with proper configuration.
Two ways to do this. First, have the testRuntime configuration extend from provided.
configurations {
provided
testRuntime.extendsFrom(provided)
}
Second, you could add the provided configuration to the classpath of your test task.
test {
classpath += configurations.provided
}
Fixed with one additional line in configurations. Don't know if it's the best and a proper solution but works as intended.
configurations {
provided
testCompile.extendsFrom(provided)
}
my case
withType<Jar> {
enabled = true
isZip64 = true
duplicatesStrategy = DuplicatesStrategy.EXCLUDE
archiveFileName.set("$project.jar")
from(sourceSets.main.get().output)
dependsOn(configurations.compileClasspath)
from({
configurations.compileClasspath.get().filter {
it.name.endsWith("jar")
}.map { zipTree(it) }
}) {
exclude("META-INF/*.RSA", "META-INF/*.SF", "META-INF/*.DSA")
}
}

Categories