diff --git a/build-logic/composeLint/README.md b/build-logic/composeLint/README.md new file mode 100644 index 000000000..7e7b81a4f --- /dev/null +++ b/build-logic/composeLint/README.md @@ -0,0 +1,25 @@ +# Setup + +This plugin automatically adds the lint to all modules defined in the whole project and +use [lint.xml](../../lint.xml) as the single source of truth to configure the lints in every app + +To enable these compose lints in a new project, follow these steps: + +1. Make sure your top level settings.gradle.kts defines the following if not already done in order to import Core's composite + build: + +```kts +pluginManagement { + includeBuild("Core/build-logic") +} +``` + +2. Inside the top-level build.gradle.kts add the following plugin: + +```kts +plugins { + id("com.infomaniak.core.compose.lint") +} +``` + +And you're done! diff --git a/build-logic/composeLint/build.gradle.kts b/build-logic/composeLint/build.gradle.kts new file mode 100644 index 000000000..28b1c2c0b --- /dev/null +++ b/build-logic/composeLint/build.gradle.kts @@ -0,0 +1,16 @@ +plugins { + `kotlin-dsl` +} + +dependencies { + compileOnly(core.gradle.build.tools) +} + +gradlePlugin { + plugins { + register("coreComposeLint") { + id = "com.infomaniak.core.compose.lint" + implementationClass = "com.infomaniak.core.compose.lint.ComposeLintPlugin" + } + } +} diff --git a/build-logic/composeLint/src/main/kotlin/com/infomaniak/core/compose/lint/ComposeLintPlugin.kt b/build-logic/composeLint/src/main/kotlin/com/infomaniak/core/compose/lint/ComposeLintPlugin.kt new file mode 100644 index 000000000..44938e1ba --- /dev/null +++ b/build-logic/composeLint/src/main/kotlin/com/infomaniak/core/compose/lint/ComposeLintPlugin.kt @@ -0,0 +1,48 @@ +/* + * Infomaniak Core - Android + * Copyright (C) 2025 Infomaniak Network SA + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ +package com.infomaniak.core.compose.lint + +import org.gradle.api.Plugin +import org.gradle.api.Project +import org.gradle.api.artifacts.VersionCatalogsExtension +import org.gradle.kotlin.dsl.configure +import org.gradle.kotlin.dsl.dependencies +import org.gradle.kotlin.dsl.getByType + +/** + * Automatically adds the lint to all modules defined in the whole project and use Core/lint.xml as the single source of truth to + * configure the lints in every app. + */ +class ComposeLintPlugin : Plugin { + override fun apply(target: Project) { + target.subprojects { + plugins.withId("com.android.base") { + extensions.configure { + lint { + lintConfig = rootProject.file("Core/lint.xml") + } + } + + val coreVersionCatalog = extensions.getByType().named("core") + dependencies { + add("lintChecks", coreVersionCatalog.findLibrary("compose-lint-checks").get()) + } + } + } + } +} diff --git a/build-logic/settings.gradle.kts b/build-logic/settings.gradle.kts index ff4aa983e..43e6182f6 100644 --- a/build-logic/settings.gradle.kts +++ b/build-logic/settings.gradle.kts @@ -12,4 +12,7 @@ dependencyResolutionManagement { rootProject.name = "build-logic" -include(":composite") +include( + ":composite", + ":composeLint", +) diff --git a/build.gradle.kts b/build.gradle.kts index 98436c73d..8145a87b6 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -53,3 +53,11 @@ android { } } } + +subprojects { + plugins.withId("com.android.base") { + dependencies { + lintChecks(core.compose.lint.checks) + } + } +} diff --git a/gradle/core.versions.toml b/gradle/core.versions.toml index 2d8add401..4bd2a8e2e 100644 --- a/gradle/core.versions.toml +++ b/gradle/core.versions.toml @@ -11,6 +11,7 @@ biometricKtx = "1.2.0-alpha05" coil = "3.3.0" coil2 = "2.7.0" # Coil2 is used in old Legacy modules only composeBom = "2025.12.00" +composeLintChecks = "1.4.2" concurrentFuturesKtx = "1.3.0" constraintLayout = "2.2.1" coordinatorLayout = "1.3.0" @@ -90,8 +91,9 @@ coil-two-gif = { module = "io.coil-kt:coil-gif", version.ref = "coil2" } coil-video = { module = "io.coil-kt.coil3:coil-video", version.ref = "coil" } compose-bom = { module = "androidx.compose:compose-bom", version.ref = "composeBom" } compose-foundation = { module = "androidx.compose.foundation:foundation" } -compose-material3 = { module = "androidx.compose.material3:material3" } +compose-lint-checks = { module = "com.slack.lint.compose:compose-lint-checks", version.ref = "composeLintChecks" } compose-material-icons = { group = "androidx.compose.material", name = "material-icons-core" } +compose-material3 = { module = "androidx.compose.material3:material3" } compose-runtime = { module = "androidx.compose.runtime:runtime" } compose-ui = { module = "androidx.compose.ui:ui" } compose-ui-android = { module = "androidx.compose.ui:ui-android" } @@ -102,6 +104,7 @@ constraintlayout = { module = "androidx.constraintlayout:constraintlayout", vers coordinatorlayout = { module = "androidx.coordinatorlayout:coordinatorlayout", version.ref = "coordinatorLayout" } firebase-messaging-ktx = { module = "com.google.firebase:firebase-messaging-ktx", version.ref = "firebaseMessaging" } foundation-android = { module = "androidx.compose.foundation:foundation-android" } +gradle-build-tools = { module = "com.android.tools.build:gradle", version.ref = "agp" } gson = { module = "com.google.code.gson:gson", version.ref = "gson" } hilt-android = { module = "com.google.dagger:hilt-android", version.ref = "hiltAndroid" } hilt-compiler = { module = "com.google.dagger:hilt-compiler", version.ref = "hiltAndroid" } diff --git a/lint.xml b/lint.xml new file mode 100644 index 000000000..a163611c6 --- /dev/null +++ b/lint.xml @@ -0,0 +1,21 @@ + + + + +