All Downloads are FREE. Search and download functionalities are using the official Maven repository.

main.name.remal.gradle_plugins.plugins.kotlin.KotlinJvmSettingsPlugin.kt Maven / Gradle / Ivy

There is a newer version: 1.9.2
Show newest version
package name.remal.gradle_plugins.plugins.kotlin

import name.remal.KotlinAllOpen
import name.remal.debug
import name.remal.gradle_plugins.api.BuildTimeConstants.getClassName
import name.remal.gradle_plugins.dsl.ApplyOptionalPlugins
import name.remal.gradle_plugins.dsl.ApplyPluginClasses
import name.remal.gradle_plugins.dsl.BaseReflectiveProjectPlugin
import name.remal.gradle_plugins.dsl.Plugin
import name.remal.gradle_plugins.dsl.PluginAction
import name.remal.gradle_plugins.dsl.PluginActionsGroup
import name.remal.gradle_plugins.dsl.WithPlugins
import name.remal.gradle_plugins.dsl.WithPluginsOptional
import name.remal.gradle_plugins.dsl.extensions.all
import name.remal.gradle_plugins.dsl.extensions.doSetupIfAndAfterEvaluate
import name.remal.gradle_plugins.dsl.extensions.get
import name.remal.gradle_plugins.dsl.extensions.isTargetJava8Compatible
import name.remal.gradle_plugins.dsl.extensions.makeSrcDirsUnique
import name.remal.gradle_plugins.dsl.extensions.setupTasksDependenciesAfterEvaluateOrNow
import name.remal.gradle_plugins.dsl.extensions.targetJavaVersion
import name.remal.gradle_plugins.plugins.common.CommonSettingsPlugin
import name.remal.gradle_plugins.plugins.java.JavaSettingsPlugin
import name.remal.isClassExists
import name.remal.version.Version
import org.gradle.api.Project
import org.gradle.api.plugins.ExtensionContainer
import org.gradle.api.plugins.PluginContainer
import org.gradle.api.plugins.UnknownPluginException
import org.gradle.api.tasks.SourceSetContainer
import org.gradle.api.tasks.TaskContainer
import org.gradle.api.tasks.compile.AbstractCompile
import org.jetbrains.kotlin.allopen.gradle.AllOpenExtension
import org.jetbrains.kotlin.gradle.plugin.KaptExtension
import org.jetbrains.kotlin.gradle.plugin.KotlinPluginWrapper
import org.jetbrains.kotlin.gradle.tasks.KotlinCompile

@Plugin(
    id = "name.remal.kotlin-settings",
    description = "Plugin that configures Kotlin plugins if some of them are applied.",
    tags = ["kotlin"]
)
@WithPlugins(KotlinJvmPluginId::class)
@ApplyPluginClasses(CommonSettingsPlugin::class, JavaSettingsPlugin::class)
@ApplyOptionalPlugins(
    KotlinPluginAllOpenPluginId::class,
    KotlinPluginJpaPluginId::class,
    KotlinPluginNoArgPluginId::class,
    KotlinPluginSpringPluginId::class
)
class KotlinJvmSettingsPlugin : BaseReflectiveProjectPlugin() {

    companion object {
        private val kotlinPluginWrapperClassName = getClassName(KotlinPluginWrapper::class.java)
        private val isKotlinPluginWrapperClassAvailable = isClassExists(kotlinPluginWrapperClassName, KotlinJvmSettingsPlugin::class.java.classLoader)
    }


    @PluginAction(order = Int.MAX_VALUE)
    fun SourceSetContainer.`Make source directories unique for all SourceSets`(project: Project) {
        project.setupTasksDependenciesAfterEvaluateOrNow {
            all {
                arrayOf(it.java, it.allJava, it.resources, it.allSource).forEach {
                    it.makeSrcDirsUnique()
                }
            }
        }
    }

    @PluginActionsGroup
    inner class `For all KotlinCompile tasks` {

        @PluginAction("If targetCompatibility is Java 8 compatible, set jvmTarget, javaParameters = true and add -Xjvm-default=compatibility compiler flag")
        fun TaskContainer.setJvmTarget(plugins: PluginContainer) {
            all(KotlinCompile::class.java) {
                it.doSetupIfAndAfterEvaluate(AbstractCompile::isTargetJava8Compatible) { task ->
                    task.kotlinOptions.run {
                        val kotlinPluginVersion = plugins.kotlinPluginVersion
                        val isJvmTarget9Supported: Boolean = (kotlinPluginVersion ?: Version.create(9999999)) >= Version.create(1, 3, 30)
                        if (isJvmTarget9Supported) {
                            jvmTarget = task.targetJavaVersion.toString()
                        } else {
                            jvmTarget = "1.8"
                        }

                        javaParameters = true

                        val isJvmDefaultSupported: Boolean = kotlinPluginVersion == null || kotlinPluginVersion >= Version.create(1, 2, 60)
                        if (isJvmDefaultSupported && freeCompilerArgs.none { it.startsWith("-Xjvm-default=") }) {
                            freeCompilerArgs += "-Xjvm-default=compatibility"
                        }
                    }
                }
            }
        }

        private val PluginContainer.kotlinPluginVersion: Version?
            get() = if (isKotlinPluginWrapperClassAvailable) {
                kotlinPluginVersionImpl
            } else {
                null
            }

        private val PluginContainer.kotlinPluginVersionImpl: Version?
            get() {
                try {
                    return getPlugin(KotlinPluginWrapper::class.java).kotlinPluginVersion.let(Version::parseOrNull)
                } catch (e: UnknownPluginException) {
                    logger.debug(e)
                    return null
                }
            }

    }

    @WithPluginsOptional(KotlinPluginKaptPluginId::class)
    @PluginActionsGroup(order = Int.MAX_VALUE)
    inner class `If 'all-kapt' Kotlin plugin is applied` {

        @PluginAction("Set kapt.correctErrorTypes = true if 'kapt' Kotlin plugin enabled")
        fun ExtensionContainer.`setKaptCorrectErrorTypes`() {
            this[KaptExtension::class.java].correctErrorTypes = true
        }

    }

    @WithPluginsOptional(KotlinPluginAllOpenPluginId::class)
    @PluginActionsGroup(order = Int.MAX_VALUE)
    inner class `If 'all-open' Kotlin plugin is applied` {

        @PluginAction(value = "name.remal.KotlinAllOpen")
        fun ExtensionContainer.name_remal_KotlinAllOpen() {
            this[AllOpenExtension::class.java].annotation(KotlinAllOpen::class.java.name)
        }

        @PluginAction(value = "javax.inject.Inject")
        fun ExtensionContainer.javax_inject_Inject() {
            this[AllOpenExtension::class.java].annotation("javax.inject.Inject")
        }

    }

}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy