Improve code quality with ktlint, detekt, and git hooks
Code quality nowadays is not only a paper of QA professionals and the code review step is not the moment to point out code style/code smells issues. That job is a job that can perfectly be done by machines, and I’m going to show how to set up a simple but effective process to improve the code of your Android or Kotlin based projects.
ktlint
ktlint defines itself as:
An anti-bikeshedding Kotlin linter with built-in formatter
A lint is is a tool that analyzes source code to flag programming errors, bugs, and stylistic errors. So ktlint does that job with Kotlin programming language.
The official lib is called ktlint but we are going to another lib that conveniently creates Gradle tasks that runs ktlint to check or format your code, ktlint-gradle. Lets code!
Create a new Android (or kotlin only)project and ktlint-gradle to your top-level project build.gradle file:
Use the latest stable release of ktlint-gradle
And within allprojects section, apply the ktlint-gradle plugin to be able to use ktlint tasks through all your other modules.
Now sync your project. Opening the Gradle section of Android Studio (shift, shift and search for “Gradle”), you will see new tasks available in the verification and formating folder.
To run the ktlintCheck open a new terminal window run:
./gradlew ktlintCheck
You will get errors that can and cannot be automatically fixed.
For those who can be, run:
./gradlew ktlintFormat
Then correct any errors that cannot be automatically fixed (eg. wildcard import). And run:
./gradlew ktlintCheck
And it will pass with no errors.
detekt
ktlint is focused on code formatting, whereas detekt is about code analysis, including code complexity, code smells, etc)
Both can be run together with no conflicts. Let's add detekt.
and configure the plugin:
Run the task DetektGenerateConfig to create a file in /config/detekt/detekt.yml that holds the standard rules.
You can edit the configuration file to match the rigor that you need. Read the documentation to find what each rule means.
Git Hooks
Git hooks (not Github hooks) are scripts that fire when something occurs, like a push or a commit.
Let's create a git hook to check lint errors and code smells on commit.
.git/hooks/pre-commit
And make it executable, otherwise, the hook is going to be ignored:
chmod a+x .git/hooks/pre-commit
Making a pre-commit hook instead of a pre-push hook or even wait for the CI to point the lint error is a more clever approach because it will reduce the number of commits needed for a feature or a fix to be done.
TODO
- Add semantic commit checking in the pre-commit hook
Based on:
https://www.youtube.com/watch?v=eysVDO2_X0s
https://www.youtube.com/watch?v=b-AWsOmszWk
https://proandroiddev.com/ooga-chaka-git-hooks-to-enforce-code-quality-11ce8d0d23cb