import org.jetbrains.kotlin.gradle.tasks.KotlinCompile import java.io.File plugins { kotlin("jvm") version "2.4.10" kotlin("plugin.serialization") version "2.4.10" } group = "io.github.sor2171" version = "1.0-SNAPSHOT" dependencies { implementation("org.jetbrains.kotlin:kotlin-reflect") implementation("org.jetbrains.kotlinx:kotlinx-coroutines-reactor:1.11.0") implementation("org.jetbrains.kotlinx:kotlinx-datetime:0.8.0") implementation("org.jetbrains.kotlinx:kotlinx-serialization-json:1.11.0") testImplementation(platform("org.junit:junit-bom:6.1.2")) testImplementation("org.junit.jupiter:junit-jupiter:6.1.3") testRuntimeOnly("org.junit.platform:junit-platform-launcher:6.1.3") } java { toolchain { languageVersion = JavaLanguageVersion.of(21) } } kotlin { compilerOptions { freeCompilerArgs.addAll( "-Xjsr305=strict", "-Xannotation-default-target=param-property" ) jvmToolchain(21) } sourceSets.main { kotlin.srcDir("build/generated/ksp/main/kotlin") } } repositories { mavenCentral() } private val skipFalseRegex = Regex("""@file:SkipCompile\s*\(\s*skip\s*=\s*false\s*\)""") private val skipTrueRegex = Regex("""^\s*@file:SkipCompile\b""", RegexOption.MULTILINE) private fun shouldSkip(file: File): Boolean { if (file.extension != "kt") return false val text = file.readText() if (!skipTrueRegex.containsMatchIn(text)) return false if (skipFalseRegex.containsMatchIn(text)) return false return true } val allSourceDirs: List = sourceSets .flatMap { it.allSource.srcDirs } .distinct() val skipFilesProvider = providers.provider { allSourceDirs.asSequence() .filter { it.exists() } .flatMap { root -> root.walkTopDown().filter { it.isFile && shouldSkip(it) } } .map { it.absolutePath } .toSet() } tasks.withType().configureEach { val skipFiles = skipFilesProvider inputs.files(allSourceDirs.map { fileTree(it) { include("**/*.kt") } }) .withPropertyName("skipCompileScan") .withPathSensitivity(PathSensitivity.RELATIVE) .ignoreEmptyDirectories() .optional() exclude { details -> details.file.extension == "kt" && skipFiles.get().contains(details.file.absolutePath) } doFirst { val skipped = skipFiles.get().filter { it.startsWith(projectDir.absolutePath) } if (skipped.isNotEmpty()) { println("[SkipCompile] $path 跳过 ${skipped.size} 个文件:") skipped.sorted().forEach { println(" - $it") } } } } tasks.withType().configureEach { failOnNoDiscoveredTests = false } tasks.test { useJUnitPlatform() }