docs/contributing/code-quality-guide.md
This document provides comprehensive guidelines for maintaining high code quality in the Thunderbird for Android project. Following these guidelines ensures that the codebase remains:
We use static analysis tools to automatically detect code quality issues and enforce standards.
Android Lint checks for potential bugs, optimization opportunities, and Android-specific issues:
# Run lint checks for all modules
./gradlew lint
# Run lint checks for a specific module
./gradlew :module-name:lint
Common issues detected:
The project's lint configuration is in config/lint/lint.xml. You can customize lint rules for specific modules by
adding a lint block to the module's build.gradle.kts file:
android {
lint {
abortOnError = false
warningsAsErrors = false
// Ignore specific issues
disable += listOf("InvalidPackage", "MissingTranslation")
// Enable specific issues
enable += listOf("RtlHardcoded", "RtlCompat", "RtlEnabled")
}
}
Detekt analyzes Kotlin code for code smells, complexity issues, and potential bugs:
# Run detekt for all modules
./gradlew detekt
# Run detekt for a specific module
./gradlew :module-name:detekt
Detekt checks for:
The project's Detekt configuration is defined in the config/detekt/detekt.yml file. This file specifies which rules
to apply and their severity levels. The detekt plugin is configured in the
build-plugin/src/main/kotlin/thunderbird.quality.detekt.gradle.kts file.
Spotless ensures consistent code formatting across the codebase:
# Check if code formatting meets standards
./gradlew spotlessCheck
# Apply automatic formatting fixes
./gradlew spotlessApply
Spotless enforces:
The project's Spotless plugin is configured in the
build-plugin/src/main/kotlin/thunderbird.quality.spotless.gradle.kts file. We use ktlint for Kotlin formatting.
The rules are defined in the .editorconfig file and as editorconfig overrides in the Spotless configuration.
configure<SpotlessExtension> {
kotlin {
target(
"src/*/java/*.kt",
"src/*/kotlin/*.kt",
"src/*/java/**/*.kt",
"src/*/kotlin/**/*.kt",
)
ktlint(libs.versions.ktlint.get())
.setEditorConfigPath("${project.rootProject.projectDir}/.editorconfig")
.editorConfigOverride(
mapOf(
"ktlint_code_style" to "intellij_idea",
"ktlint_standard_function-signature" to "disabled",
),
)
}
}
For Markdown we use Flexmark and no further configuration is needed.
The project follows the Kotlin style guide with some project-specific adaptations:
camelCase for variables, functions, and methodsPascalCase for classes, interfaces, enums and type parametersUPPER_SNAKE_CASE for constants and enum constantsDefault or a specific name, e.g.:DefaultEmailRepository implements EmailRepositoryInMemoryCache implements Cache./gradlew spotlessApply to enforce formatting automaticallyval (immutable) over var when possible?., ?:, requireNotNull, checkNotNull)map, filter, etc.) for cleaner codedata classes for model objectscoroutines for asynchronous operationsflow for reactive programmingViewModel, LifecycleOwner)Security is critical. Always:
Comprehensive testing is a critical aspect of code quality.
Key expectations:
π See Testing Guide for frameworks, patterns, and CI coverage rules.
The project uses GitHub Actions for continuous integration. Each pull request triggers automated checks for:
The CI configuration is defined in the .github/workflows directory. The main workflow file is android.yml, which
defines the CI pipeline for Android builds.
π See Code Review Guide for PR expectations and etiquette.