Skip to content

Commit

Permalink
Contribute dependencies selectively to generation process
Browse files Browse the repository at this point in the history
  • Loading branch information
MiSikora committed May 21, 2024
1 parent e5893e8 commit 2ef4f48
Show file tree
Hide file tree
Showing 28 changed files with 648 additions and 12 deletions.
16 changes: 16 additions & 0 deletions docs/changelog.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,22 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
disabledFeature("Feature")
}
```
- Dependencies can now selectively contribute to generation process.
```groovy
laboratory {
featureFactory()
featureSourceFactory()
sourcedStorage()
optionFactory()
dependency(project(":feature"), [
DependencyContribution.FeatureFactory,
DependencyContribution.FeatureSourceFactory,
DependencyContribution.OptionFactory,
DependencyContribution.SourcedStorage,
])
}
```

### Changed
- Gradle tasks are now always registered when plugin is applied in a project. If there is nothing to generate tasks will clear their respective output directories.
Expand Down
3 changes: 3 additions & 0 deletions docs/gradle-plugin.md
Original file line number Diff line number Diff line change
Expand Up @@ -658,6 +658,9 @@ laboratory {
// Includes feature flags that are used for generation of feature factories, sourced storage and option factory.
dependency(project(":some-project"))
// By default dependency contributes to all declared generators but it can be selectively applied
// by passing a contribution list.
dependency(project(":some-project"), [DependencyContribution.FeatureFactory, DependencyContribution.OptionFactory])
// If typesafe project accessors are enabled.
dependency(projects.someProject)
}
Expand Down
14 changes: 14 additions & 0 deletions laboratory/gradle-plugin/api/gradle-plugin.api
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,16 @@ public final class io/mehow/laboratory/gradle/ChildFeatureFlagsInput : java/io/S
public final fun feature (Ljava/lang/String;Lorg/gradle/api/Action;)V
}

public final class io/mehow/laboratory/gradle/DependencyContribution : java/lang/Enum {
public static final field FeatureFactory Lio/mehow/laboratory/gradle/DependencyContribution;
public static final field FeatureSourceFactory Lio/mehow/laboratory/gradle/DependencyContribution;
public static final field OptionFactory Lio/mehow/laboratory/gradle/DependencyContribution;
public static final field SourcedStorage Lio/mehow/laboratory/gradle/DependencyContribution;
public static fun getEntries ()Lkotlin/enums/EnumEntries;
public static fun valueOf (Ljava/lang/String;)Lio/mehow/laboratory/gradle/DependencyContribution;
public static fun values ()[Lio/mehow/laboratory/gradle/DependencyContribution;
}

public final class io/mehow/laboratory/gradle/DeprecationLevel : java/lang/Enum {
public static final field Error Lio/mehow/laboratory/gradle/DeprecationLevel;
public static final field Hidden Lio/mehow/laboratory/gradle/DeprecationLevel;
Expand Down Expand Up @@ -68,7 +78,11 @@ public final class io/mehow/laboratory/gradle/FeatureFlagInput$MultiOption : io/
public abstract class io/mehow/laboratory/gradle/LaboratoryExtension {
public fun <init> ()V
public final fun dependency (Lorg/gradle/api/Project;)V
public final fun dependency (Lorg/gradle/api/Project;Ljava/util/Collection;)V
public final fun dependency (Lorg/gradle/api/internal/catalog/DelegatingProjectDependency;)V
public final fun dependency (Lorg/gradle/api/internal/catalog/DelegatingProjectDependency;Ljava/util/Collection;)V
public static synthetic fun dependency$default (Lio/mehow/laboratory/gradle/LaboratoryExtension;Lorg/gradle/api/Project;Ljava/util/Collection;ILjava/lang/Object;)V
public static synthetic fun dependency$default (Lio/mehow/laboratory/gradle/LaboratoryExtension;Lorg/gradle/api/internal/catalog/DelegatingProjectDependency;Ljava/util/Collection;ILjava/lang/Object;)V
public final fun disabledFeature (Ljava/lang/String;)V
public final fun disabledFeature (Ljava/lang/String;Lorg/gradle/api/Action;)V
public static synthetic fun disabledFeature$default (Lio/mehow/laboratory/gradle/LaboratoryExtension;Ljava/lang/String;Lorg/gradle/api/Action;ILjava/lang/Object;)V
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package io.mehow.laboratory.gradle

/**
* Possible contributions of a dependency to feature flag generation. See [LaboratoryExtension.dependency]
* for more info.
*/
public enum class DependencyContribution {
/** Contribute to [LaboratoryExtension.featureFactory]. */
FeatureFactory,

/** Contribute to [LaboratoryExtension.featureSourceFactory]. */
FeatureSourceFactory,

/** Contribute to [LaboratoryExtension.optionFactory]. */
OptionFactory,

/** Contribute to [LaboratoryExtension.sourcedStorage]. */
SourcedStorage,
}
Original file line number Diff line number Diff line change
Expand Up @@ -20,9 +20,13 @@ public abstract class LaboratoryExtension {

private val packageNameProvider = PackageNameProvider()

private val mutableDependencies = mutableListOf<FeatureFlagInput>()
private val externalDependencies = mutableMapOf<DependencyContribution, List<FeatureFlagInput>>()

internal val factoryFeatureFlags get() = featureFlags + mutableDependencies
internal val factoryFeatureFlags get() = buildMap {
DependencyContribution.entries.forEach { entry ->
put(entry, featureFlags + externalDependencies[entry].orEmpty())
}
}

internal lateinit var project: Project

Expand Down Expand Up @@ -147,21 +151,38 @@ public abstract class LaboratoryExtension {

/**
* Includes a [project] during feature flags contribution to [featureFactory], [featureSourcesFactory],
* [sourcedStorage] or [optionFactory]. Included project must have Laboratory plugin applied.
* [sourcedStorage] or [optionFactory]. Contribution can be selective applied by supplying [contributeTo] collection.
*
* Included project must have Laboratory plugin applied.
*/
public fun dependency(project: DelegatingProjectDependency) {
dependency(project.dependencyProject)
@JvmOverloads
public fun dependency(
project: DelegatingProjectDependency,
contributeTo: Collection<DependencyContribution> = DependencyContribution.entries,
) {
dependency(project.dependencyProject, contributeTo)
}

/**
* Includes a [project] during feature flags contribution to [featureFactory], [featureSourcesFactory],
* [sourcedStorage] or [optionFactory]. Included project must have Laboratory plugin applied.
* [sourcedStorage] or [optionFactory]. Contribution can be selective applied by supplying [contributeTo] collection.
*
* Included project must have Laboratory plugin applied.
*/
public fun dependency(project: Project) {
@JvmOverloads
public fun dependency(
project: Project,
contributeTo: Collection<DependencyContribution> = DependencyContribution.entries,
) {
require(contributeTo.isNotEmpty()) {
"Dependency in project '${this.project.name}' on '${project.name}' must have at least one contribution"
}
this.project.evaluationDependsOn(project.path)
val laboratoryExtension = requireNotNull(project.extensions.findByType(LaboratoryExtension::class.java)) {
"Cannot depend on a project without laboratory plugin"
}
mutableDependencies += laboratoryExtension.featureFlags
contributeTo.forEach { entry ->
externalDependencies[entry] = externalDependencies[entry].orEmpty() + laboratoryExtension.featureFlags
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ public class LaboratoryPlugin : Plugin<Project> {
task.group = PluginName
task.description = "Generate feature factory"
task.factory.set(extension.factoryInput)
task.features.set(extension.factoryFeatureFlags)
task.features.set(extension.factoryFeatureFlags.getValue(DependencyContribution.FeatureFactory))
task.outputDirectory.set(layout.buildDirectory.dir("generated/laboratory/code/feature-factory"))
}
}
Expand All @@ -75,7 +75,7 @@ public class LaboratoryPlugin : Plugin<Project> {
task.group = PluginName
task.description = "Generate sourced feature storage"
task.storage.set(extension.storageInput)
task.features.set(extension.factoryFeatureFlags)
task.features.set(extension.factoryFeatureFlags.getValue(DependencyContribution.SourcedStorage))
task.outputDirectory.set(layout.buildDirectory.dir("generated/laboratory/code/sourced-storage"))
}
}
Expand All @@ -88,7 +88,7 @@ public class LaboratoryPlugin : Plugin<Project> {
task.group = PluginName
task.description = "Generate option factory"
task.factory.set(extension.optionFactoryInput)
task.features.set(extension.factoryFeatureFlags)
task.features.set(extension.factoryFeatureFlags.getValue(DependencyContribution.OptionFactory))
task.outputDirectory.set(layout.buildDirectory.dir("generated/laboratory/code/option-factory"))
}
}
Expand All @@ -101,7 +101,7 @@ public class LaboratoryPlugin : Plugin<Project> {
task.group = PluginName
task.description = "Generate feature source factory"
task.factory.set(extension.featureSourcesFactory)
task.features.set(extension.factoryFeatureFlags)
task.features.set(extension.factoryFeatureFlags.getValue(DependencyContribution.FeatureSourceFactory))
task.outputDirectory.set(layout.buildDirectory.dir("generated/laboratory/code/feature-source-factory"))
}
}
Expand Down
Loading

0 comments on commit 2ef4f48

Please sign in to comment.