Codementor Events

Refactor your Kotlin code with built-in extension functions

Published Aug 03, 2020

Today at work, I was fixing a bug in a Kotlin code which has been written some time ago. At a first glance, there was nothing obvious that stood out:

fun getTrimmedPropId(propId: String): String? {
            if (!Utils.emptyOrNull(propId)) {
                val tokens = propId.split("/").toTypedArray()
                    .filter { it.isNotEmpty() }
                return tokens[tokens.size - 1]
            }
            return null
        }

However, I quickly realised that propId was being passed as null to thr function, which obviously was wrong as this function does not permit nullable propId.
I am personally glad that Kotlin forces us to be explicit in our intentions and that we must declare that we do or don't expect a null parameter.

At the end, the fix was easy:

fun getTrimmedPropId(propId: String?): String? 

However, as I often do, I looked at the function body again to see if I could clean it up and streamline it a little so I have ended up with the code that looks more Kotlin than the previous one:

fun getTrimmedPropId(propId: String?): String? {
  return propId
    	.orEmpty()
        .split("/")
        .lastOrNull { it.isNotEmpty() }
}

I have made use of a couple of String and List extension functions to achieve this more streamlined and easier to follow code.

Firstly, I was able to remove the null check if statement by using orEmpty() on the propId which is an extension function on a nullable String that returns the string if its not null otherwise empty string. It is really handy when trying to reduce a number of if statements in your code.

Lastly, this tokens[tokens.size - 1] was very dangerous piece of code if the tokens array ever happened to be empty. This code was just taking last element in the array and was easily substitutable with lastOrNull(), an extension function on a Collection object. This variant takes a lambda function that retrieves the last non empty string from the list.

It is worth mentioning that we have had Unit tests in place for getTrimmedPropId() function and I was glad to see all tests pass upon refactoring.

Key takeaways:

  • Explore Kotlin extension functions on the most common classes, such as String, List, Int etc. There are a lot of them to discover
  • Write your own extension functions for the operations that you may need in several places and communicate them to your team so they can also benefit from them
  • Write unit tests even for the smallest piece of business logic. You will thank youself for writing them when you need to refactor your code in the future
Discover and read more posts from Adrian Lesniak
get started