aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPaweł Marks <pmarks@virtuslab.com>2020-06-30 21:05:16 +0200
committerPaweł Marks <Kordyjan@users.noreply.github.com>2020-07-07 10:07:21 +0200
commit9b7e163ae69272c7e56088d6f256d6b19f9a01d4 (patch)
tree333c56d610ae7e612d9f49d579e4931f7e8f9863
parent33cf9d62f409dd5d98678fdcd29227763af11586 (diff)
downloaddokka-9b7e163ae69272c7e56088d6f256d6b19f9a01d4.tar.gz
dokka-9b7e163ae69272c7e56088d6f256d6b19f9a01d4.tar.bz2
dokka-9b7e163ae69272c7e56088d6f256d6b19f9a01d4.zip
Refactor Extension DSL and remove fallback mechanism
-rw-r--r--core/src/main/kotlin/plugability/DokkaContext.kt33
-rw-r--r--core/src/main/kotlin/plugability/DokkaPlugin.kt17
-rw-r--r--core/src/main/kotlin/plugability/extensions.kt101
-rw-r--r--plugins/base/src/main/kotlin/DokkaBase.kt24
4 files changed, 68 insertions, 107 deletions
diff --git a/core/src/main/kotlin/plugability/DokkaContext.kt b/core/src/main/kotlin/plugability/DokkaContext.kt
index 15349ff0..12b1557b 100644
--- a/core/src/main/kotlin/plugability/DokkaContext.kt
+++ b/core/src/main/kotlin/plugability/DokkaContext.kt
@@ -46,7 +46,7 @@ inline fun <reified T : DokkaPlugin> DokkaContext.plugin(): T = plugin(T::class)
?: throw java.lang.IllegalStateException("Plugin ${T::class.qualifiedName} is not present in context.")
interface DokkaContextConfiguration {
- fun addExtensionDependencies(extension: Extension<*>)
+ fun addExtensionDependencies(extension: Extension<*, *, *>)
}
private class DokkaContextConfigurationImpl(
@@ -55,7 +55,7 @@ private class DokkaContextConfigurationImpl(
) : DokkaContext, DokkaContextConfiguration {
private val plugins = mutableMapOf<KClass<*>, DokkaPlugin>()
private val pluginStubs = mutableMapOf<KClass<*>, DokkaPlugin>()
- internal val extensions = mutableMapOf<ExtensionPoint<*>, MutableList<Extension<*>>>()
+ val extensions = mutableMapOf<ExtensionPoint<*>, MutableList<Extension<*, *, *>>>()
val pointsUsed: MutableSet<ExtensionPoint<*>> = mutableSetOf()
val pointsPopulated: MutableSet<ExtensionPoint<*>> = mutableSetOf()
override val unusedPoints: Set<ExtensionPoint<*>>
@@ -67,14 +67,14 @@ private class DokkaContextConfigurationImpl(
VISITED;
}
- internal val verticesWithState = mutableMapOf<Extension<*>, State>()
- internal val adjacencyList: MutableMap<Extension<*>, MutableList<Extension<*>>> = mutableMapOf()
+ val verticesWithState = mutableMapOf<Extension<*, *, *>, State>()
+ val adjacencyList: MutableMap<Extension<*, *, *>, MutableList<Extension<*, *, *>>> = mutableMapOf()
private fun topologicalSort() {
- val result: MutableList<Extension<*>> = mutableListOf()
+ val result: MutableList<Extension<*, *, *>> = mutableListOf()
- fun visit(n: Extension<*>) {
+ fun visit(n: Extension<*, *, *>) {
val state = verticesWithState[n]
if (state == State.VISITED)
return
@@ -107,14 +107,11 @@ private class DokkaContextConfigurationImpl(
)
pointsUsed += point
- val extensions = extensions[point].orEmpty() as List<Extension<T>>
+ val extensions = extensions[point].orEmpty() as List<Extension<T, *, *>>
return when (extensions.size) {
0 -> throwBadArity("none was")
1 -> extensions.single().action.get(this)
- else -> {
- val notFallbacks = extensions.filterNot { it.isFallback }
- if (notFallbacks.size == 1) notFallbacks.single().action.get(this) else throwBadArity("many were")
- }
+ else -> throwBadArity("many were")
}
}
@@ -132,13 +129,15 @@ private class DokkaContextConfigurationImpl(
plugin.internalInstall(this, this.configuration)
}
- override fun addExtensionDependencies(extension: Extension<*>) {
- val orderDsl = OrderDsl()
- extension.ordering?.invoke(orderDsl)
+ override fun addExtensionDependencies(extension: Extension<*, *, *>) {
+ if (extension.ordering is OrderingKind.ByDsl) {
+ val orderDsl = OrderDsl()
+ extension.ordering.block.invoke(orderDsl)
- verticesWithState += extension to State.UNVISITED
- adjacencyList.getOrPut(extension, ::mutableListOf) += orderDsl.following.toList()
- orderDsl.previous.forEach { adjacencyList.getOrPut(it, ::mutableListOf) += extension }
+ verticesWithState += extension to State.UNVISITED
+ adjacencyList.getOrPut(extension, ::mutableListOf) += orderDsl.following.toList()
+ orderDsl.previous.forEach { adjacencyList.getOrPut(it, ::mutableListOf) += extension }
+ }
}
fun logInitialisationInfo() {
diff --git a/core/src/main/kotlin/plugability/DokkaPlugin.kt b/core/src/main/kotlin/plugability/DokkaPlugin.kt
index 7ead43b8..bf82daa7 100644
--- a/core/src/main/kotlin/plugability/DokkaPlugin.kt
+++ b/core/src/main/kotlin/plugability/DokkaPlugin.kt
@@ -7,8 +7,6 @@ import kotlin.reflect.KProperty
import kotlin.reflect.KProperty1
import kotlin.reflect.full.createInstance
-private typealias ExtensionDelegate<T> = ReadOnlyProperty<DokkaPlugin, Extension<T>>
-
abstract class DokkaPlugin {
private val extensionDelegates = mutableListOf<KProperty<*>>()
@@ -25,15 +23,10 @@ abstract class DokkaPlugin {
)
}
- protected fun <T : Any> extending(isFallback: Boolean = false, definition: ExtendingDSL.() -> Extension<T>) =
- if (isFallback) {
- ExtensionProvider { definition().markedAsFallback() }
- } else {
- ExtensionProvider(definition)
- }
+ protected fun <T : Any> extending(definition: ExtendingDSL.() -> Extension<T, *, *>) = ExtensionProvider(definition)
protected class ExtensionProvider<T : Any> internal constructor(
- private val definition: ExtendingDSL.() -> Extension<T>
+ private val definition: ExtendingDSL.() -> Extension<T, *, *>
) {
operator fun provideDelegate(thisRef: DokkaPlugin, property: KProperty<*>) = lazy {
ExtendingDSL(
@@ -45,7 +38,7 @@ abstract class DokkaPlugin {
internal fun internalInstall(ctx: DokkaContextConfiguration, configuration: DokkaConfiguration) {
extensionDelegates.asSequence()
- .filterIsInstance<KProperty1<DokkaPlugin, Extension<*>>>() // should be always true
+ .filterIsInstance<KProperty1<DokkaPlugin, Extension<*, *, *>>>() // should be always true
.map { it.get(this) }
.forEach { if (it.condition.invoke(configuration)) ctx.addExtensionDependencies(it) }
}
@@ -76,8 +69,8 @@ fun throwIllegalQuery(): Nothing =
inline fun <reified T : DokkaPlugin, reified R : ConfigurableBlock> configuration(context: DokkaContext): ReadOnlyProperty<Any?, R> {
return object : ReadOnlyProperty<Any?, R> {
override fun getValue(thisRef: Any?, property: KProperty<*>): R {
- return context.configuration.pluginsConfiguration.get(T::class.qualifiedName
- ?: throw AssertionError("Plugin must be named class")).let {
+ return context.configuration.pluginsConfiguration[T::class.qualifiedName
+ ?: throw AssertionError("Plugin must be named class")].let {
Gson().fromJson(it, R::class.java)
}
}
diff --git a/core/src/main/kotlin/plugability/extensions.kt b/core/src/main/kotlin/plugability/extensions.kt
index 20b60469..c6dd0b85 100644
--- a/core/src/main/kotlin/plugability/extensions.kt
+++ b/core/src/main/kotlin/plugability/extensions.kt
@@ -9,79 +9,43 @@ data class ExtensionPoint<T : Any> internal constructor(
override fun toString() = "ExtensionPoint: $pluginClass/$pointName"
}
-abstract class Extension<T : Any> internal constructor(
+sealed class OrderingKind {
+ object None : OrderingKind()
+ class ByDsl(val block: (OrderDsl.() -> Unit)) : OrderingKind()
+}
+
+sealed class OverrideKind {
+ object None : OverrideKind()
+ class Present(val overriden: Extension<*, *, *>) : OverrideKind()
+}
+
+class Extension<T : Any, Ordering : OrderingKind, Override : OverrideKind> internal constructor(
internal val extensionPoint: ExtensionPoint<T>,
internal val pluginClass: String,
internal val extensionName: String,
internal val action: LazyEvaluated<T>,
- internal val ordering: (OrderDsl.() -> Unit)? = null,
- internal val conditions: Array<DokkaConfiguration.() -> Boolean> = emptyArray(),
- internal val isFallback: Boolean
+ internal val ordering: Ordering,
+ internal val override: Override,
+ internal val conditions: List<DokkaConfiguration.() -> Boolean>
) {
override fun toString() = "Extension: $pluginClass/$extensionName"
override fun equals(other: Any?) =
- if (other is Extension<*>) this.pluginClass == other.pluginClass && this.extensionName == other.extensionName
+ if (other is Extension<*, *, *>) this.pluginClass == other.pluginClass && this.extensionName == other.extensionName
else false
override fun hashCode() = listOf(pluginClass, extensionName).hashCode()
- abstract fun addCondition(condition: (DokkaConfiguration.() -> Boolean)): Extension<T>
-
- abstract fun markedAsFallback(): Extension<T>
-
- open val condition: DokkaConfiguration.() -> Boolean
- get() = { conditions.all { it(this) }}
+ val condition: DokkaConfiguration.() -> Boolean
+ get() = { conditions.all { it(this) } }
}
-class ExtensionOrdered<T : Any> internal constructor(
+private fun <T : Any> Extension(
extensionPoint: ExtensionPoint<T>,
pluginClass: String,
extensionName: String,
- action: LazyEvaluated<T>,
- ordering: (OrderDsl.() -> Unit),
- conditions: Array<DokkaConfiguration.() -> Boolean> = emptyArray(),
- isFallback: Boolean = false
-) : Extension<T>(
- extensionPoint,
- pluginClass,
- extensionName,
- action,
- ordering,
- conditions,
- isFallback
-) {
- override fun addCondition(condition: DokkaConfiguration.() -> Boolean) =
- ExtensionOrdered(extensionPoint, pluginClass, extensionName, action, ordering!!, conditions + condition)
-
- override fun markedAsFallback() =
- ExtensionOrdered(extensionPoint, pluginClass, extensionName, action, ordering!!, conditions, true)
-}
-
-class ExtensionUnordered<T : Any> internal constructor(
- extensionPoint: ExtensionPoint<T>,
- pluginClass: String,
- extensionName: String,
- action: LazyEvaluated<T>,
- conditions: Array<DokkaConfiguration.() -> Boolean> = emptyArray(),
- isFallback: Boolean = false
-) : Extension<T>(
- extensionPoint,
- pluginClass,
- extensionName,
- action,
- null,
- conditions,
- isFallback
-) {
- override fun addCondition(condition: DokkaConfiguration.() -> Boolean) =
- ExtensionUnordered(extensionPoint, pluginClass, extensionName, action, conditions + condition)
-
- override fun markedAsFallback() =
- ExtensionUnordered(extensionPoint, pluginClass, extensionName, action, conditions, true)
-}
-
-internal data class Ordering(val previous: Set<Extension<*>>, val following: Set<Extension<*>>)
+ action: LazyEvaluated<T>
+) = Extension(extensionPoint, pluginClass, extensionName, action, OrderingKind.None, OverrideKind.None, emptyList())
@DslMarker
annotation class ExtensionsDsl
@@ -90,29 +54,34 @@ annotation class ExtensionsDsl
class ExtendingDSL(private val pluginClass: String, private val extensionName: String) {
infix fun <T : Any> ExtensionPoint<T>.with(action: T) =
- ExtensionUnordered(this, this@ExtendingDSL.pluginClass, extensionName, LazyEvaluated.fromInstance(action))
+ Extension(this, this@ExtendingDSL.pluginClass, extensionName, LazyEvaluated.fromInstance(action))
infix fun <T : Any> ExtensionPoint<T>.providing(action: (DokkaContext) -> T) =
- ExtensionUnordered(this, this@ExtendingDSL.pluginClass, extensionName, LazyEvaluated.fromRecipe(action))
+ Extension(this, this@ExtendingDSL.pluginClass, extensionName, LazyEvaluated.fromRecipe(action))
- infix fun <T : Any> ExtensionUnordered<T>.order(block: OrderDsl.() -> Unit) =
- ExtensionOrdered(extensionPoint, pluginClass, extensionName, action, block)
+ infix fun <T : Any, Override : OverrideKind> Extension<T, OrderingKind.None, Override>.order(
+ block: OrderDsl.() -> Unit
+ ) = Extension(extensionPoint, pluginClass, extensionName, action, OrderingKind.ByDsl(block), override, conditions)
- infix fun <T : Any> Extension<T>.applyIf(condition: DokkaConfiguration.() -> Boolean): Extension<T> =
- this.addCondition(condition)
+ infix fun <T : Any, Override : OverrideKind, Ordering: OrderingKind> Extension<T, Ordering, Override>.applyIf(
+ condition: DokkaConfiguration.() -> Boolean
+ ) = Extension(extensionPoint, pluginClass, extensionName, action, ordering, override, conditions + condition)
+ infix fun <T : Any, Override : OverrideKind, Ordering: OrderingKind> Extension<T, Ordering, Override>.override(
+ overriden: Extension<T, *, *>
+ ) = Extension(extensionPoint, pluginClass, extensionName, action, ordering, OverrideKind.Present(overriden), conditions)
}
@ExtensionsDsl
class OrderDsl {
- internal val previous = mutableSetOf<Extension<*>>()
- internal val following = mutableSetOf<Extension<*>>()
+ internal val previous = mutableSetOf<Extension<*, *, *>>()
+ internal val following = mutableSetOf<Extension<*, *, *>>()
- fun after(vararg extensions: Extension<*>) {
+ fun after(vararg extensions: Extension<*, *, *>) {
previous += extensions
}
- fun before(vararg extensions: Extension<*>) {
+ fun before(vararg extensions: Extension<*, *, *>) {
following += extensions
}
} \ No newline at end of file
diff --git a/plugins/base/src/main/kotlin/DokkaBase.kt b/plugins/base/src/main/kotlin/DokkaBase.kt
index 0e535c86..8fed0afd 100644
--- a/plugins/base/src/main/kotlin/DokkaBase.kt
+++ b/plugins/base/src/main/kotlin/DokkaBase.kt
@@ -55,19 +55,19 @@ class DokkaBase : DokkaPlugin() {
}
}
- val documentableMerger by extending(isFallback = true) {
+ val documentableMerger by extending {
CoreExtensions.documentableMerger with DefaultDocumentableMerger
}
- val deprecatedDocumentableFilter by extending(isFallback = true) {
+ val deprecatedDocumentableFilter by extending {
CoreExtensions.preMergeDocumentableTransformer providing ::DeprecatedDocumentableFilterTransformer
}
- val documentableVisbilityFilter by extending(isFallback = true) {
+ val documentableVisbilityFilter by extending {
CoreExtensions.preMergeDocumentableTransformer providing ::DocumentableVisibilityFilterTransformer
}
- val emptyPackagesFilter by extending(isFallback = true) {
+ val emptyPackagesFilter by extending {
CoreExtensions.preMergeDocumentableTransformer providing ::EmptyPackagesFilterTransformer order {
after(deprecatedDocumentableFilter, documentableVisbilityFilter)
}
@@ -77,13 +77,13 @@ class DokkaBase : DokkaPlugin() {
CoreExtensions.documentableTransformer with ActualTypealiasAdder()
}
- val modulesAndPackagesDocumentation by extending(isFallback = true) {
+ val modulesAndPackagesDocumentation by extending {
CoreExtensions.preMergeDocumentableTransformer providing { ctx ->
ModuleAndPackageDocumentationTransformer(ctx, ctx.single(kotlinAnalysis))
}
}
- val kotlinSignatureProvider by extending(isFallback = true) {
+ val kotlinSignatureProvider by extending {
signatureProvider providing { ctx ->
KotlinSignatureProvider(ctx.single(commentsToContentConverter), ctx.logger)
}
@@ -106,7 +106,7 @@ class DokkaBase : DokkaPlugin() {
CoreExtensions.documentableTransformer with ExtensionExtractorTransformer()
}
- val documentableToPageTranslator by extending(isFallback = true) {
+ val documentableToPageTranslator by extending {
CoreExtensions.documentableToPageTranslator providing { ctx ->
DefaultDocumentableToPageTranslator(
ctx.single(commentsToContentConverter),
@@ -116,7 +116,7 @@ class DokkaBase : DokkaPlugin() {
}
}
- val docTagToContentConverter by extending(isFallback = true) {
+ val docTagToContentConverter by extending {
commentsToContentConverter with DocTagToContentConverter
}
@@ -138,11 +138,11 @@ class DokkaBase : DokkaPlugin() {
CoreExtensions.renderer providing ::HtmlRenderer applyIf { format == "html" }
}
- val defaultKotlinAnalysis by extending(isFallback = true) {
+ val defaultKotlinAnalysis by extending {
kotlinAnalysis providing { ctx -> KotlinAnalysis(ctx) }
}
- val locationProvider by extending(isFallback = true) {
+ val locationProvider by extending {
locationProviderFactory providing ::DefaultLocationProviderFactory
}
@@ -154,7 +154,7 @@ class DokkaBase : DokkaPlugin() {
externalLocationProviderFactory with DokkaExternalLocationProviderFactory()
}
- val fileWriter by extending(isFallback = true) {
+ val fileWriter by extending {
outputWriter providing ::FileWriter
}
@@ -211,7 +211,7 @@ class DokkaBase : DokkaPlugin() {
htmlPreprocessors providing ::SourcesetDependencyAppender order { after(rootCreator) }
}
- val allModulePageCreators by extending(isFallback = true) {
+ val allModulePageCreators by extending {
CoreExtensions.allModulePageCreator providing {
MultimodulePageCreator(it)
}