package org.jetbrains.dokka.dokkatoo.tests.integration import org.jetbrains.dokka.dokkatoo.utils.* import org.jetbrains.dokka.dokkatoo.utils.GradleProjectTest.Companion.projectTestTempDir import io.kotest.core.spec.style.FunSpec import io.kotest.matchers.file.shouldBeAFile import io.kotest.matchers.file.shouldHaveSameStructureAndContentAs import io.kotest.matchers.file.shouldHaveSameStructureAs import io.kotest.matchers.shouldBe import io.kotest.matchers.string.shouldContain import io.kotest.matchers.string.shouldNotContain import java.io.File /** * Integration test for the `it-basic` project in Dokka * * Runs Dokka & Dokkatoo, and compares the resulting HTML site. */ class BasicProjectIntegrationTest : FunSpec({ val tempDir = projectTestTempDir.resolve("it/it-basic").toFile() val dokkatooProject = initDokkatooProject(tempDir.resolve("dokkatoo")) val dokkaProject = initDokkaProject(tempDir.resolve("dokka")) context("when generating HTML") { dokkaProject.runner .addArguments( "clean", "dokkaHtml", "--stacktrace", ) .forwardOutput() .build { context("with Dokka") { test("expect project builds successfully") { output shouldContain "BUILD SUCCESSFUL" } } } dokkatooProject.runner .addArguments( "clean", "dokkatooGeneratePublicationHtml", "--stacktrace", ) .forwardOutput() .build { context("with Dokkatoo") { test("expect project builds successfully") { output shouldContain "BUILD SUCCESSFUL" } test("expect all dokka workers are successful") { dokkatooProject .findFiles { it.name == "dokka-worker.log" } .shouldBeSingleton { dokkaWorkerLog -> dokkaWorkerLog.shouldBeAFile() dokkaWorkerLog.readText().shouldNotContainAnyOf( "[ERROR]", "[WARN]", ) } } } } test("expect the same HTML is generated") { val dokkaHtmlDir = dokkaProject.projectDir.resolve("build/dokka/html") val dokkatooHtmlDir = dokkatooProject.projectDir.resolve("build/dokka/html") val expectedFileTree = dokkaHtmlDir.toTreeString() val actualFileTree = dokkatooHtmlDir.toTreeString() println((actualFileTree to expectedFileTree).sideBySide()) expectedFileTree shouldBe actualFileTree dokkatooHtmlDir.toFile().shouldHaveSameStructureAs(dokkaHtmlDir.toFile()) dokkatooHtmlDir.toFile().shouldHaveSameStructureAndContentAs(dokkaHtmlDir.toFile()) } test("Dokkatoo tasks should be cacheable") { dokkatooProject.runner .addArguments( "dokkatooGeneratePublicationHtml", "--stacktrace", "--build-cache", ) .forwardOutput() .build { output shouldContainAll listOf( "Task :dokkatooGeneratePublicationHtml UP-TO-DATE", ) } } context("expect Dokkatoo is compatible with Gradle Configuration Cache") { dokkatooProject.file(".gradle/configuration-cache").toFile().deleteRecursively() dokkatooProject.file("build/reports/configuration-cache").toFile().deleteRecursively() val configCacheRunner = dokkatooProject.runner .addArguments( "clean", "dokkatooGeneratePublicationHtml", "--stacktrace", "--no-build-cache", "--configuration-cache", ) .forwardOutput() test("first build should store the configuration cache") { configCacheRunner.build { output shouldContain "BUILD SUCCESSFUL" output shouldContain "Configuration cache entry stored" output shouldNotContain "problems were found storing the configuration cache" } } test("second build should reuse the configuration cache") { configCacheRunner.build { output shouldContain "BUILD SUCCESSFUL" output shouldContain "Configuration cache entry reused" } } } } }) private fun initDokkaProject( destinationDir: File, ): GradleProjectTest { return GradleProjectTest(destinationDir.toPath()).apply { copyIntegrationTestProject("it-basic/dokka") buildGradleKts = buildGradleKts .replace( // no idea why this needs to be changed """file("../customResources/""", """file("./customResources/""", ) } } private fun initDokkatooProject( destinationDir: File, ): GradleProjectTest { return GradleProjectTest(destinationDir.toPath()).apply { copyIntegrationTestProject("it-basic/dokkatoo") } }