Skip to content

Commit e65ba3b

Browse files
committed
Make the plugin output directory configurable
Make outputDir configurable, so that users can have full control over the output path. Additionally, the GenerateJavaTask lazy by converting inputs to gradle Properties. See: https://docs.gradle.org/current/userguide/lazy_configuration.html
1 parent 2c3fb8b commit e65ba3b

File tree

4 files changed

+220
-106
lines changed

4 files changed

+220
-106
lines changed

graphql-dgs-codegen-gradle/src/main/kotlin/com/netflix/graphql/dgs/codegen/gradle/CodegenPlugin.kt

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,8 @@ class CodegenPlugin : Plugin<Project> {
4444
val javaConvention = project.convention.getPlugin(JavaPluginConvention::class.java)
4545
val sourceSets = javaConvention.sourceSets
4646
val mainSourceSet = sourceSets.getByName(SourceSet.MAIN_SOURCE_SET_NAME)
47-
val outputDir = generateJavaTaskProvider.map(GenerateJavaTask::getOutputDir)
47+
val outputDir = generateJavaTaskProvider.flatMap(GenerateJavaTask::outputDir)
48+
4849
mainSourceSet.java.srcDirs(project.files(outputDir).builtBy(generateJavaTaskProvider))
4950

5051
project.afterEvaluate { p ->

graphql-dgs-codegen-gradle/src/main/kotlin/com/netflix/graphql/dgs/codegen/gradle/GenerateJavaTask.kt

Lines changed: 134 additions & 93 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,14 @@ import com.netflix.graphql.dgs.codegen.CodeGen
2222
import com.netflix.graphql.dgs.codegen.CodeGenConfig
2323
import com.netflix.graphql.dgs.codegen.Language
2424
import org.gradle.api.DefaultTask
25+
import org.gradle.api.file.DirectoryProperty
26+
import org.gradle.api.file.ProjectLayout
27+
import org.gradle.api.model.ObjectFactory
28+
import org.gradle.api.provider.ListProperty
29+
import org.gradle.api.provider.MapProperty
30+
import org.gradle.api.provider.Property
31+
import org.gradle.api.provider.ProviderFactory
32+
import org.gradle.api.provider.SetProperty
2533
import org.gradle.api.tasks.CacheableTask
2634
import org.gradle.api.tasks.Input
2735
import org.gradle.api.tasks.InputFiles
@@ -30,133 +38,166 @@ import org.gradle.api.tasks.PathSensitive
3038
import org.gradle.api.tasks.PathSensitivity
3139
import org.gradle.api.tasks.TaskAction
3240
import org.jetbrains.kotlin.gradle.plugin.KotlinPluginWrapper
33-
import java.io.File
3441
import java.nio.file.Paths
35-
import java.util.*
42+
import java.util.Locale
43+
import javax.inject.Inject
3644

3745
@CacheableTask
38-
open class GenerateJavaTask : DefaultTask() {
39-
@Input
40-
var generatedSourcesDir: String = project.buildDir.absolutePath
46+
abstract class GenerateJavaTask @Inject constructor(
47+
projectLayout: ProjectLayout,
48+
providerFactory: ProviderFactory,
49+
objectFactory: ObjectFactory
50+
) : DefaultTask() {
51+
@get:Input
52+
val generatedSourcesDir: Property<String> = objectFactory.property(String::class.java)
53+
.convention(projectLayout.buildDirectory.map { it.asFile.absolutePath })
4154

4255
@PathSensitive(PathSensitivity.RELATIVE)
43-
@InputFiles
44-
var schemaPaths = mutableListOf<Any>("${project.projectDir}/src/main/resources/schema")
45-
46-
@Input
47-
var packageName = "com.netflix.dgs.codegen.generated"
48-
49-
@Input
50-
var subPackageNameClient = "client"
51-
52-
@Input
53-
var subPackageNameDatafetchers = "datafetchers"
54-
55-
@Input
56-
var subPackageNameTypes = "types"
57-
58-
private val hasKotlinPluginWrapperClass = try {
59-
this.javaClass.classLoader.loadClass("org.jetbrains.kotlin.gradle.plugin.KotlinPluginWrapper")
60-
true
61-
} catch (ex: Exception) {
62-
false
63-
}
64-
65-
@Input
66-
var language = if (hasKotlinPluginWrapperClass && project.plugins.hasPlugin(KotlinPluginWrapper::class.java)) "KOTLIN" else "JAVA"
56+
@get:InputFiles
57+
val schemaPaths: ListProperty<Any> = objectFactory.listProperty(Any::class.java)
58+
.convention(listOf(projectLayout.projectDirectory.dir("src/main/resources/schema").toString()))
59+
60+
@get:Input
61+
val packageName: Property<String> = objectFactory.property(String::class.java)
62+
.convention("com.netflix.dgs.codegen.generated")
63+
64+
@get:Input
65+
val subPackageNameClient: Property<String> = objectFactory.property(String::class.java)
66+
.convention("client")
67+
68+
@get:Input
69+
val subPackageNameDatafetchers: Property<String> = objectFactory.property(String::class.java)
70+
.convention("datafetchers")
71+
72+
@get:Input
73+
val subPackageNameTypes: Property<String> = objectFactory.property(String::class.java)
74+
.convention("types")
75+
76+
@get:Input
77+
val language: Property<String> = objectFactory.property(String::class.java)
78+
.convention(
79+
providerFactory.provider {
80+
val hasKotlinPluginWrapperClass = try {
81+
this.javaClass.classLoader.loadClass("org.jetbrains.kotlin.gradle.plugin.KotlinPluginWrapper")
82+
true
83+
} catch (ex: Exception) {
84+
false
85+
}
86+
if (hasKotlinPluginWrapperClass && project.plugins.hasPlugin(KotlinPluginWrapper::class.java)) "KOTLIN" else "JAVA"
87+
}
88+
)
6789

68-
@Input
69-
var typeMapping = mutableMapOf<String, String>()
90+
@get:Input
91+
val typeMapping: MapProperty<String, String> = objectFactory.mapProperty(String::class.java, String::class.java)
7092

71-
@Input
72-
var generateBoxedTypes = false
93+
@get:Input
94+
val generateBoxedTypes: Property<Boolean> = objectFactory.property(Boolean::class.java)
95+
.convention(false)
7396

74-
@Input
75-
var generateClient = false
97+
@get:Input
98+
val generateClient: Property<Boolean> = objectFactory.property(Boolean::class.java)
99+
.convention(false)
76100

77-
@Input
78-
var generateDataTypes = true
101+
@get:Input
102+
val generateDataTypes: Property<Boolean> = objectFactory.property(Boolean::class.java)
103+
.convention(true)
79104

80-
@Input
81-
var generateInterfaces = false
105+
@get:Input
106+
val generateInterfaces: Property<Boolean> = objectFactory.property(Boolean::class.java)
107+
.convention(false)
82108

83-
@Input
84-
var generateInterfaceSetters = true
109+
@get:Input
110+
val generateInterfaceSetters: Property<Boolean> = objectFactory.property(Boolean::class.java)
111+
.convention(true)
85112

86-
@OutputDirectory
87-
fun getOutputDir(): File {
88-
return Paths.get("$generatedSourcesDir/generated/sources/dgs-codegen").toFile()
89-
}
113+
@get:OutputDirectory
114+
val outputDir: DirectoryProperty = objectFactory.directoryProperty()
115+
.convention(
116+
generatedSourcesDir.flatMap { baseDir ->
117+
projectLayout.dir(providerFactory.provider { project.file("$baseDir/generated/sources/dgs-codegen") })
118+
}
119+
)
90120

91-
@OutputDirectory
92-
fun getExampleOutputDir(): File {
93-
return Paths.get("$generatedSourcesDir/generated/sources/dgs-codegen-generated-examples").toFile()
94-
}
121+
@get:OutputDirectory
122+
val exampleOutputDir: DirectoryProperty = objectFactory.directoryProperty()
123+
.convention(
124+
generatedSourcesDir.flatMap { baseDir ->
125+
projectLayout.dir(providerFactory.provider { project.file("$baseDir/generated/sources/dgs-codegen-generated-examples") })
126+
}
127+
)
95128

96-
@Input
97-
var includeQueries = mutableListOf<String>()
129+
@get:Input
130+
val includeQueries: SetProperty<String> = objectFactory.setProperty(String::class.java)
98131

99-
@Input
100-
var includeMutations = mutableListOf<String>()
132+
@get:Input
133+
val includeMutations: SetProperty<String> = objectFactory.setProperty(String::class.java)
101134

102-
@Input
103-
var includeSubscriptions = mutableListOf<String>()
135+
@get:Input
136+
val includeSubscriptions: SetProperty<String> = objectFactory.setProperty(String::class.java)
104137

105-
@Input
106-
var skipEntityQueries = false
138+
@get:Input
139+
val skipEntityQueries: Property<Boolean> = objectFactory.property(Boolean::class.java)
140+
.convention(false)
107141

108-
@Input
109-
var shortProjectionNames = false
142+
@get:Input
143+
val shortProjectionNames: Property<Boolean> = objectFactory.property(Boolean::class.java)
144+
.convention(false)
110145

111-
@Input
112-
var omitNullInputFields = false
146+
@get:Input
147+
val omitNullInputFields: Property<Boolean> = objectFactory.property(Boolean::class.java)
148+
.convention(false)
113149

114-
@Input
115-
var maxProjectionDepth = 10
150+
@get:Input
151+
val maxProjectionDepth: Property<Int> = objectFactory.property(Int::class.javaObjectType)
152+
.convention(10)
116153

117-
@Input
118-
var kotlinAllFieldsOptional = false
154+
@get:Input
155+
val kotlinAllFieldsOptional: Property<Boolean> = objectFactory.property(Boolean::class.java)
156+
.convention(false)
119157

120-
@Input
121-
var snakeCaseConstantNames = false
158+
@get:Input
159+
val snakeCaseConstantNames: Property<Boolean> = objectFactory.property(Boolean::class.java)
160+
.convention(false)
122161

123162
@TaskAction
124163
fun generate() {
125-
val schemaPaths = schemaPaths.map { Paths.get(it.toString()).toFile() }.sorted().toSet()
126-
schemaPaths.filter { !it.exists() }.forEach {
127-
logger.warn("Schema location ${it.absolutePath} does not exist")
164+
val schemaPaths = schemaPaths.get().asSequence()
165+
.map { Paths.get(it.toString()).toFile() }
166+
.toSortedSet()
167+
schemaPaths.asSequence().filter { !it.exists() }.forEach {
168+
logger.warn("Schema location {} does not exist", it.absolutePath)
128169
}
129170
logger.info("Processing schema files:")
130171
schemaPaths.forEach {
131-
logger.info("Processing $it")
172+
logger.info("Processing {}", it)
132173
}
133174

134175
val config = CodeGenConfig(
135176
schemas = emptySet(),
136177
schemaFiles = schemaPaths,
137-
outputDir = getOutputDir().toPath(),
138-
examplesOutputDir = getExampleOutputDir().toPath(),
178+
outputDir = outputDir.get().asFile.toPath(),
179+
examplesOutputDir = exampleOutputDir.get().asFile.toPath(),
139180
writeToFiles = true,
140-
packageName = packageName,
141-
subPackageNameClient = subPackageNameClient,
142-
subPackageNameDatafetchers = subPackageNameDatafetchers,
143-
subPackageNameTypes = subPackageNameTypes,
144-
language = Language.valueOf(language.uppercase(Locale.getDefault())),
145-
generateBoxedTypes = generateBoxedTypes,
146-
generateClientApi = generateClient,
147-
generateInterfaces = generateInterfaces,
148-
generateInterfaceSetters = generateInterfaceSetters,
149-
typeMapping = typeMapping,
150-
includeQueries = includeQueries.toSet(),
151-
includeMutations = includeMutations.toSet(),
152-
includeSubscriptions = includeSubscriptions.toSet(),
153-
skipEntityQueries = skipEntityQueries,
154-
shortProjectionNames = shortProjectionNames,
155-
generateDataTypes = generateDataTypes,
156-
omitNullInputFields = omitNullInputFields,
157-
maxProjectionDepth = maxProjectionDepth,
158-
kotlinAllFieldsOptional = kotlinAllFieldsOptional,
159-
snakeCaseConstantNames = snakeCaseConstantNames
181+
packageName = packageName.get(),
182+
subPackageNameClient = subPackageNameClient.get(),
183+
subPackageNameDatafetchers = subPackageNameDatafetchers.get(),
184+
subPackageNameTypes = subPackageNameTypes.get(),
185+
language = Language.valueOf(language.get().uppercase(Locale.getDefault())),
186+
generateBoxedTypes = generateBoxedTypes.get(),
187+
generateClientApi = generateClient.get(),
188+
generateInterfaces = generateInterfaces.get(),
189+
generateInterfaceSetters = generateInterfaceSetters.get(),
190+
typeMapping = typeMapping.get(),
191+
includeQueries = includeQueries.get(),
192+
includeMutations = includeMutations.get(),
193+
includeSubscriptions = includeSubscriptions.get(),
194+
skipEntityQueries = skipEntityQueries.get(),
195+
shortProjectionNames = shortProjectionNames.get(),
196+
generateDataTypes = generateDataTypes.get(),
197+
omitNullInputFields = omitNullInputFields.get(),
198+
maxProjectionDepth = maxProjectionDepth.get(),
199+
kotlinAllFieldsOptional = kotlinAllFieldsOptional.get(),
200+
snakeCaseConstantNames = snakeCaseConstantNames.get()
160201
)
161202

162203
logger.info("Codegen config: {}", config)

0 commit comments

Comments
 (0)