Dariusz Kuc
07/27/2021, 5:23 PMcompileKotlin in JVM builds and compile${Variant}Kotlin for 🤖 ). What is somewhat weird is that for JVM builds my task gets included when running build goal but on Android it is not....
If I explicitly run my task on Android project it does get finalized correctly. So just wondering what would be the cause of the difference in behavior between JVM and Android buildsDariusz Kuc
07/27/2021, 5:25 PMfinalizeBy -> https://github.com/dariuszkuc/graphql-kotlin/blob/android_build/plugins/graphql-ko[…]n/com/expediagroup/graphql/plugin/gradle/GraphQLGradlePlugin.ktDariusz Kuc
07/27/2021, 5:27 PMcompileKotlin dependsOn myTask vs current myTask finalizedBy compileKotlin) but I thought that was considered a bad practice?Vampire
07/27/2021, 9:19 PMdependsOn if you can instead use an implicit task dependency, yes.
But using a finalizedBy instead is just wrong and thus worse.
compileKotlin dependsOn myTask means if compileKotlin needs to run, first myTask has to have been run before it.
myTask finalizedBy compileKotlin means whenever myTask is run, run compileKotlin automatically after it.
But the latter does not mean, that if you run compileKotlin, that myTask is run before.
But either way, if you do it like that, I guess you generate the sources into the same directory where the versioned sources are present, which is another bad practice.
Or you manually add the output directory of myTask to the source directories, which also is bad practice.
Instead you should register the myTask as source directory, then its output will be considered source for all means like building a sources jar, requesting all sources, compilation and so on and at the same time you have the implicit task dependency for all tasks that need the sources and not only the compile task.Vampire
07/27/2021, 9:20 PMval mySourceGeneratingTask by tasks.registering(...) {
...
}
val generate by tasks.registering {
dependsOn(mySourceGeneratingTask)
}
sourceSets {
main {
java {
srcDir(mySourceGeneratingTask)
}
}
}
The generate task is fully optional, but I like to have a lifecycle task that depends on all tasks that generate something.Dariusz Kuc
07/27/2021, 9:23 PMsrcDir -> https://github.com/dariuszkuc/graphql-kotlin/blob/android_build/plugins/graphql-ko[…]n/com/expediagroup/graphql/plugin/gradle/GraphQLGradlePlugin.ktDariusz Kuc
07/27/2021, 9:23 PMmain.java.srcDirDariusz Kuc
07/27/2021, 9:24 PMDariusz Kuc
07/27/2021, 9:25 PMOr you manually add the output directory ofyeah I'm adding output directoryto the source directories, which also is bad practice.myTask
Dariusz Kuc
07/27/2021, 9:37 PMsrcDir and that works like a charm for JVM build (without explicit dependsOn/finalizeBy), I'll check what I need to do for AndroidVampire
07/27/2021, 9:57 PMoutputDirectory DirectoryProperty property should also be enough already.
I didn't check, but I guess outputDirectory is annotated with @OutputDirectory, this way it also carries the implicit task dependency.
So even with what you had before it should have been fine without dependsOn or finalizedBy and for Android there is hopefully also a place to add the source.
But I'm not familiar with Android builds, sorry.Dariusz Kuc
07/27/2021, 10:04 PMDariusz Kuc
07/27/2021, 10:14 PMDariusz Kuc
07/28/2021, 4:31 AMsourceSets are stored -> on default JVM build its a project property vs android extension property
val baseExtension = project.extensions.findByType(BaseExtension::class.java)
println("Android source sets: ${baseExtension?.sourceSets?.names}")
val androidMainSourceSet = baseExtension?.sourceSets?.findByName("main")?.java
androidMainSourceSet?.srcDir(task.outputDirectory)
println("Android main source set: $androidMainSourceSet")
Running it I see that my task source is added but it still doesn't run during the build
Android source sets: [androidTest, androidTestDebug, androidTestRelease, debug, main, release, test, testDebug, testRelease]
Android main source set: com.android.build.gradle.internal.api.DefaultAndroidSourceDirectorySet@1b4062a2, type=com.android.build.gradle.internal.api.artifact.SourceArtifactType$JAVA_SOURCES@9aa5534, source=[src/main/java, task ':app:graphqlGenerateClient' property 'outputDirectory']
Wondering whether this is because of kotlin-android plugin is applied eagerly (supposedly getting fix in next release).Vampire
07/28/2021, 7:45 AM@Override
@NonNull
public Set<File> getSrcDirs() {
return fileResolver.resolveFiles(source.toArray()).getFiles();
}
So at this time the implicit task dependencies are eradicated. I guess you indeed need explicit dependsOn for Android and need to complain to Google about this fact.ephemient
07/28/2021, 8:50 AMVampire
07/28/2021, 9:33 AMsrcDir is not enough.
So probably what ephemient said. 🙂Dariusz Kuc
07/28/2021, 1:58 PMregisterJavaGeneratingTask but it was throwing me an exception as I'm trying to configure it from my task configuration
i.e.
val baseExtension = project.extensions.findByType(BaseExtension::class.java)!!
val androidMainSourceSet = baseExtension.sourceSets.findByName("main")?.java
androidMainSourceSet?.srcDir(task.outputDirectory)
val variants = when (androidExtension) {
is LibraryExtension -> if (isTestSource) findTestVariants(androidExtension) else androidExtension.libraryVariants
is AppExtension -> if (isTestSource) findTestVariants(androidExtension) else androidExtension.applicationVariants
else -> throw RuntimeException(
"Unsupported configuration - unable to determine appropriate compile Kotlin task. graphql-kotlin plugin only supports default JVM builds, Android libraries and applications"
)
}
variants.forEach { variant ->
variant.registerJavaGeneratingTask(task, task.outputDirectory.asFile.get()). // throws exception
variant.addJavaSourceFoldersToModel(task.outputDirectory.asFile.get())
}
DefaultTaskContainer#NamedDomainObjectProvider.configure(Action) on task set cannot be executed in the current context.
was trying to add sources directly to the variant sources (e.g. debug) as well but that didn't make any differenceDariusz Kuc
07/28/2021, 2:14 PMdependsOn on my task that will always execute my task (even though end user might not have configured it)....Dariusz Kuc
07/28/2021, 2:15 PMVampire
07/28/2021, 2:16 PMcompile task needs a dependency on your task, then add it.
If your task is unconfigured and thus has no inputs, it will be skipped if you have annotated your properties properly.Vampire
07/28/2021, 2:17 PMVampire
07/28/2021, 2:17 PMDariusz Kuc
07/28/2021, 2:22 PMIf your task is unconfigured and thus has no inputs, it will be skipped if you have annotated your properties properly.I use conventions to setup some defaults so unsure if that makes any difference
Vampire
07/28/2021, 2:38 PMVampire
07/28/2021, 2:39 PMDariusz Kuc
07/28/2021, 2:45 PMDariusz Kuc
07/28/2021, 2:46 PMDariusz Kuc
07/28/2021, 2:58 PMVampire
07/28/2021, 2:59 PMephemient
07/29/2021, 2:36 PMtask.outputDirectoty.asFile.get(),
val outputDir = File(buildDir, "generated/source/...")
taskProvider.configure { outputDirectory.set(outputDir) }
variant.registerJavaGeneratingTask(taskProvider, outputDir)
wouldn't need any trickinessVampire
07/29/2021, 2:38 PMbuildDir, but the lazy layout.buildDirectory variant 🙂Vampire
07/29/2021, 2:40 PMregisterJavaGeneratingTask which again does not accept lazy values 😞Dariusz Kuc
07/29/2021, 3:26 PMDariusz Kuc
07/29/2021, 3:28 PM