diff options
-rw-r--r-- | .idea/libraries/kotlin_compiler.xml | 66 | ||||
-rw-r--r-- | src/DocumentationBuilder.kt | 32 | ||||
-rw-r--r-- | src/DocumentationBuildingVisitor.kt | 114 | ||||
-rw-r--r-- | src/DocumentationModel.kt | 35 | ||||
-rw-r--r-- | test/data/functions/function.kt (renamed from test/data/function.kt) | 0 | ||||
-rw-r--r-- | test/data/functions/functionWithParams.kt | 4 | ||||
-rw-r--r-- | test/src/TopLevelFunctionTest.kt | 17 |
7 files changed, 243 insertions, 25 deletions
diff --git a/.idea/libraries/kotlin_compiler.xml b/.idea/libraries/kotlin_compiler.xml index f0b20ad9..8e5c6bd2 100644 --- a/.idea/libraries/kotlin_compiler.xml +++ b/.idea/libraries/kotlin_compiler.xml @@ -71,6 +71,72 @@ <root url="file://$PROJECT_DIR$/../kotlin/dependencies/download/asm-src" /> <root url="file://$PROJECT_DIR$/../kotlin/injector-generator/src" /> <root url="file://$PROJECT_DIR$/../kotlin/ide-compiler-runner/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/js/js.tests/test" /> + <root url="file://$PROJECT_DIR$/../kotlin/js/js.dart-ast/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/js/js.translator/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/j2k/tests/test" /> + <root url="file://$PROJECT_DIR$/../kotlin/core/descriptors/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/core/runtime.jvm/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/core/util.runtime/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/core/serialization/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/core/serialization.java/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/core/descriptor.loader.java/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/docs/exPuzzlers/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/idea/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/idea/tests" /> + <root url="file://$PROJECT_DIR$/../kotlin/eval4j/test" /> + <root url="file://$PROJECT_DIR$/../kotlin/grammar/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/cli/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/cli/cli-common/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/util/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/tests" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/backend/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/frontend/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/preloader/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/preloader/instrumentation/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/android-tests/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/android-tests/tests" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/android-tests/android-module/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/frontend.java/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/backend-common/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/jet.as.java.psi/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/compiler/integration-tests/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/runtime/target/copied-sources" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kdoc-maven-plugin/src/main/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kdoc-maven-plugin/src/test/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-maven-plugin/src/main/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-maven-plugin/src/test/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-gradle-plugin/src/main/kotlin" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-gradle-plugin/src/test/resources/testProject/AndroidProject/Lib/src/main/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-gradle-plugin/src/test/resources/testProject/AndroidProject/Android/src/main/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-gradle-plugin/src/test/resources/testProject/kotlinJavaProject/src/main/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-gradle-plugin/target/test-classes/testProject/AndroidProject/Lib/src/main/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-gradle-plugin/target/test-classes/testProject/AndroidProject/Android/src/main/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-gradle-plugin/target/test-classes/testProject/kotlinJavaProject/src/main/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-js-tests-junit/src/test/kotlin" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-maven-plugin-test/src/it/test-classpath/src/test/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-maven-plugin-test/src/it/test-helloworld/src/test/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-maven-plugin-test/src/it/test-inlineDisabled/src/test/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-maven-plugin-test/target/it/test-classpath/src/test/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-maven-plugin-test/target/it/test-helloworld/src/test/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-maven-plugin-test/target/it/test-inlineDisabled/src/test/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-gradle-plugin-core/src/test/resources/testProject/simpleProject/src/main/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-gradle-plugin-core/src/test/resources/testProject/additionalJavaSrc/src/main/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-gradle-plugin-core/src/test/resources/testProject/additionalJavaSrc/generated" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-gradle-plugin-core/target/test-classes/testProject/simpleProject/src/main/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-gradle-plugin-core/target/test-classes/testProject/additionalJavaSrc/src/main/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/tools/kotlin-gradle-plugin-core/target/test-classes/testProject/additionalJavaSrc/generated" /> + <root url="file://$PROJECT_DIR$/../kotlin/libraries/examples/kotlin-java-example/src/test/java" /> + <root url="file://$PROJECT_DIR$/../kotlin/generators/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/generators/tests" /> + <root url="file://$PROJECT_DIR$/../kotlin/jps-plugin/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/jps-plugin/test" /> + <root url="file://$PROJECT_DIR$/../kotlin/jps-plugin/kannotator-jps-plugin-test/test" /> + <root url="file://$PROJECT_DIR$/../kotlin/build-tools/ant/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/build-tools/core/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/dependencies/download/asm-src" /> + <root url="file://$PROJECT_DIR$/../kotlin/injector-generator/src" /> + <root url="file://$PROJECT_DIR$/../kotlin/ide-compiler-runner/src" /> </SOURCES> </library> </component>
\ No newline at end of file diff --git a/src/DocumentationBuilder.kt b/src/DocumentationBuilder.kt new file mode 100644 index 00000000..02db3540 --- /dev/null +++ b/src/DocumentationBuilder.kt @@ -0,0 +1,32 @@ +package com.jetbrains.dokka + +import org.jetbrains.jet.lang.resolve.* +import org.jetbrains.jet.lang.psi.* +import org.jetbrains.jet.lang.descriptors.* +import org.jetbrains.jet.lang.descriptors.impl.* + +fun BindingContext.createDocumentation(file: JetFile): DocumentationModel { + val model = DocumentationModel() + val packageFragment = getPackageFragment(file) + if (packageFragment == null) throw IllegalArgumentException("File $file should have package fragment") + + val visitor = DocumentationBuilderVisitor() + visitDescriptor(packageFragment, model, visitor) + + return model +} + +class DocumentationBuilderVisitor() : DeclarationDescriptorVisitorEmptyBodies<DocumentationNode, DocumentationNode>() { + + override fun visitDeclarationDescriptor(descriptor: DeclarationDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = DocumentationNode(descriptor!!.getName().asString(), "doc", DocumentationNodeKind.Function) + data?.addReferenceTo(node, DocumentationReferenceKind.Member) + return node + } + + override fun visitValueParameterDescriptor(descriptor: ValueParameterDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = DocumentationNode(descriptor!!.getName().asString(), "doc", DocumentationNodeKind.Function) + data?.addReferenceTo(node, DocumentationReferenceKind.Detail) + return node + } +} diff --git a/src/DocumentationBuildingVisitor.kt b/src/DocumentationBuildingVisitor.kt new file mode 100644 index 00000000..6486ac90 --- /dev/null +++ b/src/DocumentationBuildingVisitor.kt @@ -0,0 +1,114 @@ +package com.jetbrains.dokka + +import org.jetbrains.jet.lang.descriptors.* +import org.jetbrains.jet.lang.resolve.name.FqName + +class DocumentationBuildingVisitor(private val worker: DeclarationDescriptorVisitor<DocumentationNode, DocumentationNode>) +: DeclarationDescriptorVisitor<DocumentationNode, DocumentationNode> { + + private fun visitChildren(descriptors: Collection<DeclarationDescriptor>, data: DocumentationNode) { + for (descriptor in descriptors) { + descriptor.accept(this, data) + } + } + + private fun visitChildren(descriptor: DeclarationDescriptor?, data: DocumentationNode) { + descriptor?.accept(this, data) + } + + private fun createDocumentation(descriptor: DeclarationDescriptor, data: DocumentationNode): DocumentationNode { + return descriptor.accept(worker, data) + } + + private fun processCallable(descriptor: CallableDescriptor, data: DocumentationNode): DocumentationNode { + val node = createDocumentation(descriptor, data) + visitChildren(descriptor.getTypeParameters(), node) + visitChildren(descriptor.getReceiverParameter(), node) + visitChildren(descriptor.getValueParameters(), node) + return node + } + + public override fun visitPackageFragmentDescriptor(descriptor: PackageFragmentDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = createDocumentation(descriptor!!, data!!) + visitChildren(descriptor.getMemberScope().getAllDescriptors(), node) + return node + } + + public override fun visitPackageViewDescriptor(descriptor: PackageViewDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = createDocumentation(descriptor!!, data!!) + visitChildren(descriptor.getMemberScope().getAllDescriptors(), node) + return node + } + + public override fun visitVariableDescriptor(descriptor: VariableDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = processCallable(descriptor!!, data!!) + return node + } + + public override fun visitPropertyDescriptor(descriptor: PropertyDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = processCallable(descriptor!!, data!!) + visitChildren(descriptor.getGetter(), node) + visitChildren(descriptor.getSetter(), node) + return node + } + + public override fun visitFunctionDescriptor(descriptor: FunctionDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = processCallable(descriptor!!, data!!) + return node + } + + public override fun visitTypeParameterDescriptor(descriptor: TypeParameterDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = createDocumentation(descriptor!!, data!!) + return node + } + + public override fun visitClassDescriptor(descriptor: ClassDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = createDocumentation(descriptor!!, data!!) + visitChildren(descriptor.getThisAsReceiverParameter(), node) + visitChildren(descriptor.getConstructors(), node) + visitChildren(descriptor.getTypeConstructor().getParameters(), node) + visitChildren(descriptor.getClassObjectDescriptor(), node) + visitChildren(descriptor.getDefaultType().getMemberScope().getAllDescriptors(), node) + return node + } + + public override fun visitModuleDeclaration(descriptor: ModuleDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = createDocumentation(descriptor!!, data!!) + visitChildren(descriptor.getPackage(FqName.ROOT), node) + return node + } + + public override fun visitConstructorDescriptor(constructorDescriptor: ConstructorDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = visitFunctionDescriptor(constructorDescriptor, data) + return node + } + + public override fun visitScriptDescriptor(scriptDescriptor: ScriptDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = visitClassDescriptor(scriptDescriptor!!.getClassDescriptor(), data) + return node + } + + public override fun visitValueParameterDescriptor(descriptor: ValueParameterDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = visitVariableDescriptor(descriptor, data) + return node + } + + public override fun visitPropertyGetterDescriptor(descriptor: PropertyGetterDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = visitFunctionDescriptor(descriptor, data) + return node + } + + public override fun visitPropertySetterDescriptor(descriptor: PropertySetterDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = visitFunctionDescriptor(descriptor, data) + return node + } + + public override fun visitReceiverParameterDescriptor(descriptor: ReceiverParameterDescriptor?, data: DocumentationNode?): DocumentationNode? { + val node = createDocumentation(descriptor!!, data!!) + return node + } +} + +public fun visitDescriptor(descriptor: DeclarationDescriptor, data: DocumentationNode, visitor: DeclarationDescriptorVisitor<DocumentationNode, DocumentationNode>): DocumentationNode { + return descriptor.accept(DocumentationBuildingVisitor(visitor), data) +} diff --git a/src/DocumentationModel.kt b/src/DocumentationModel.kt index 3391c277..b8ef21b0 100644 --- a/src/DocumentationModel.kt +++ b/src/DocumentationModel.kt @@ -1,7 +1,7 @@ package com.jetbrains.dokka -import com.intellij.psi.PsiFile import org.jetbrains.jet.lang.resolve.BindingContext +import org.jetbrains.jet.lang.psi.JetFile public enum class DocumentationNodeKind { Package @@ -13,7 +13,7 @@ public enum class DocumentationNodeKind { Exception Page - Module + Model } public enum class DocumentationReferenceKind { @@ -24,7 +24,7 @@ public enum class DocumentationReferenceKind { Override } -public class DocumentationNode(val name: String, val doc: String, val kind: DocumentationNodeKind) { +public open class DocumentationNode(val name: String, val doc: String, val kind: DocumentationNodeKind) { private val references = arrayListOf<DocumentationReference>() public val owner: DocumentationNode @@ -36,39 +36,28 @@ public class DocumentationNode(val name: String, val doc: String, val kind: Docu public val links: List<DocumentationNode> get() = references(DocumentationReferenceKind.Link).map { it.to } + // TODO: Should we allow node mutation? Model merge will copy by ref, so references are transparent, which could nice public fun addReferenceTo(to: DocumentationNode, kind: DocumentationReferenceKind) { references.add(DocumentationReference(this, to, kind)) } + public fun addAllReferencesFrom(other: DocumentationNode) { + references.addAll(other.references) + } + public fun references(kind: DocumentationReferenceKind): List<DocumentationReference> = references.filter { it.kind == kind } } -public class DocumentationModel { - private val items = arrayListOf<DocumentationNode>() - +public class DocumentationModel : DocumentationNode("model", "", DocumentationNodeKind.Model) { fun merge(other: DocumentationModel): DocumentationModel { val model = DocumentationModel() - model.addNodes(other.nodes) - model.addNodes(this.nodes) + model.addAllReferencesFrom(other) + model.addAllReferencesFrom(this) return model } - public fun addNode(node: DocumentationNode) { - items.add(node) - } - - public fun addNodes(nodes: List<DocumentationNode>) { - items.addAll(nodes) - } - public val nodes: List<DocumentationNode> - get() = items + get() = members } public data class DocumentationReference(val from: DocumentationNode, val to: DocumentationNode, val kind: DocumentationReferenceKind) - -fun BindingContext.createDocumentation(file: PsiFile): DocumentationModel { - val model = DocumentationModel() - model.addNode(DocumentationNode("fn", "doc", DocumentationNodeKind.Function)) - return model -}
\ No newline at end of file diff --git a/test/data/function.kt b/test/data/functions/function.kt index 878b017b..878b017b 100644 --- a/test/data/function.kt +++ b/test/data/functions/function.kt diff --git a/test/data/functions/functionWithParams.kt b/test/data/functions/functionWithParams.kt new file mode 100644 index 00000000..9d3a0ad7 --- /dev/null +++ b/test/data/functions/functionWithParams.kt @@ -0,0 +1,4 @@ +/** + * doc + */ +fun function(x : Int) {}
\ No newline at end of file diff --git a/test/src/TopLevelFunctionTest.kt b/test/src/TopLevelFunctionTest.kt index a51b7bdd..dd88a1a0 100644 --- a/test/src/TopLevelFunctionTest.kt +++ b/test/src/TopLevelFunctionTest.kt @@ -7,8 +7,8 @@ import com.jetbrains.dokka.* public class TopLevelFunctionTest { Test fun function() { - verifyFiles("test/data/function.kt") { model -> - val item = model.nodes.single() + verifyFiles("test/data/functions/function.kt") { model -> + val item = model.nodes.single().members.single() assertEquals(DocumentationNodeKind.Function, item.kind) assertEquals("fn", item.name) assertEquals("doc", item.doc) @@ -17,4 +17,17 @@ public class TopLevelFunctionTest { assertTrue(item.links.none()) } } + + Test fun functionWithParams() { + verifyFiles("test/data/functions/functionWithParams.kt") { model -> + val item = model.nodes.single().members.single() + assertEquals(DocumentationNodeKind.Function, item.kind) + assertEquals("function", item.name) + assertEquals("doc", item.doc) + assertEquals("x", item.details.single().name) + + assertTrue(item.members.none()) + assertTrue(item.links.none()) + } + } }
\ No newline at end of file |