aboutsummaryrefslogtreecommitdiff
path: root/core/src/main/kotlin/plugability/DokkaPlugin.kt
diff options
context:
space:
mode:
authorPaweł Marks <pmarks@virtuslab.com>2019-11-19 16:54:47 +0100
committerBłażej Kardyś <bkardys@virtuslab.com>2019-11-25 16:24:16 +0100
commit8a057a4611684a6a4616e136d480c005997070cd (patch)
tree47068c1ae3af98ce82a6f66c5eea52aa67d823c6 /core/src/main/kotlin/plugability/DokkaPlugin.kt
parent007aacb9ae3b228d0cef45ff5beb066b1dcd4cdc (diff)
downloaddokka-8a057a4611684a6a4616e136d480c005997070cd.tar.gz
dokka-8a057a4611684a6a4616e136d480c005997070cd.tar.bz2
dokka-8a057a4611684a6a4616e136d480c005997070cd.zip
Working extensions in plugins
Diffstat (limited to 'core/src/main/kotlin/plugability/DokkaPlugin.kt')
-rw-r--r--core/src/main/kotlin/plugability/DokkaPlugin.kt58
1 files changed, 55 insertions, 3 deletions
diff --git a/core/src/main/kotlin/plugability/DokkaPlugin.kt b/core/src/main/kotlin/plugability/DokkaPlugin.kt
index 2654bcee..60ca245c 100644
--- a/core/src/main/kotlin/plugability/DokkaPlugin.kt
+++ b/core/src/main/kotlin/plugability/DokkaPlugin.kt
@@ -1,6 +1,58 @@
package org.jetbrains.dokka.plugability
-interface DokkaPlugin {
- val name: String
- fun install(context: DokkaContext)
+import kotlin.properties.ReadOnlyProperty
+import kotlin.reflect.KProperty
+import kotlin.reflect.KProperty1
+import kotlin.reflect.KTypeProjection
+import kotlin.reflect.full.createInstance
+import kotlin.reflect.full.createType
+import kotlin.reflect.full.declaredMemberProperties
+import kotlin.reflect.jvm.isAccessible
+import kotlin.reflect.jvm.jvmErasure
+
+private typealias ExtensionDelegate<T> = ReadOnlyProperty<DokkaPlugin, Extension<T>>
+
+abstract class DokkaPlugin {
+ private val extensionDelegates = mutableListOf<KProperty<*>>()
+
+ @PublishedApi
+ internal var context: DokkaContext? = null
+
+ protected open fun install(context: DokkaContext) {}
+
+ protected inline fun <reified T : DokkaPlugin> plugin(): T =
+ context?.plugin(T::class) as? T ?: T::class.createInstance().also { it.context = this.context }
+
+ protected fun <T : Any> extensionPoint() =
+ object : ReadOnlyProperty<DokkaPlugin, ExtensionPoint<T>> {
+ override fun getValue(thisRef: DokkaPlugin, property: KProperty<*>) = ExtensionPoint<T>(
+ thisRef::class.qualifiedName ?: throw AssertionError("Plugin must be named class"),
+ property.name
+ )
+ }
+
+ protected fun <T: Any> extending(definition: ExtendingDSL.() -> Extension<T>) = ExtensionProvider(definition)
+
+ protected class ExtensionProvider<T: Any> internal constructor(
+ private val definition: ExtendingDSL.() -> Extension<T>
+ ) {
+ operator fun provideDelegate(thisRef: DokkaPlugin, property: KProperty<*>) = lazy {
+ ExtendingDSL(
+ thisRef::class.qualifiedName ?: throw AssertionError("Plugin must be named class"),
+ property.name
+ ).definition()
+ }.also { thisRef.extensionDelegates += property }
+ }
+
+ internal fun internalInstall(ctx: DokkaContext) {
+ context = ctx
+ install(ctx)
+
+ extensionDelegates.asSequence()
+ .filterIsInstance<KProperty1<DokkaPlugin, Extension<*>>>() // always true
+ .map { it.get(this) }
+ .forEach { ctx.addExtension(it) }
+ }
+
+
} \ No newline at end of file