Use Variables for Versions of Dependencies on Multi Module Android Projects, Please.

Motive

Recently I was tasked, by myself, to update all the dependencies of project containing submodules in counts of tens, to the newest version.

This was required in order to add a new dependency that itself depended on a newer version of some of the existing dependencies, think, appcompat-v7 for example.

The pain

Now that I had lousily when creating new modules on the project just let every single project get its default version of appcompat-v7 and when shared dependencies arised, just copied from existing gradle files, there was literally hundreds of dependencies that would have needed updated.

Solution

First I thought, this should be simple, right? Use the Android Studios replace all within project feature to perform the update on regex, for appcompat-v7 I would have target regex of

["']com\.android\.support:appcompat-v7:.*["']

no biggie, right? Okay, to replace with regex, the replacement must be regex, or some similar format too such as

"com\.android\.support:appcompat-v7:\$appcompatVersion"

next step would be to add this variable $appcompatVersion to the ext section of projects build.gradle, easypeasy!

Now imagine doing this for all dependencies! I for one have at least five different dependencies that are depended upon by at least ten modules in the project, such hassle!

Automation to the rescue

I don’t remember who was the wise man of internet who once said that you could automate something, even if it took longer time, because it would consume less mental energy, it would still be a win-win situation, but that’s what I have been living upon, and it has been much happier life.

I botched up a quick Java application to automate the tasks, it could and maybe should have been a python script, as its pretty simple but man, where does zebra get from their stripes?!

The application has a simple job!

  1. Take a path from comamand line arguments
  2. For that path go through each sub-folder that contains file build.gradle
    1. For this build.gradle file go through each dependency and keep track of each depency by their group, name and version
    2. Make sure versions don’t differ across project, if they do, throw exception
  3. Now we’ve got list of all dependencies and their versions!
  4. Go through all collected dependencies and create a variable name by using the group and name of the dependency, also keep track of the value of this variable, so it can be saved later on
  5. Go again through each sub-folder that contains file build.gradle
    1. This time replace all dependencies version with variable we created before
    2. backup this build.gradle and replace it with the newly created
  6. Add variable to projects build.gradle, copy and replace it
  7. Cross fingers that everything went well!

For me, this ended up creating 39 badly named variable in my projects build.gradle and much boring work was saved.

        comAndroidSupportRecyclerviewVVersion = '27.0.2'
        comAnjlabAndroidIabVLibraryVersion = '1.0.44'
        ioRequeryRequeryProcessorVersion = '1.5.0'
        comGoogleCodeGsonGsonVersion = '2.8.2'
        comFlaviofariaKenburnsviewVersion = '1.0.7'

Hmm, could this naming scheme be improved?

Success!

Now every dependencys version is defined in the project, awesome! This could and maybe should have been done by beginning of the time, but, oh well, humans ain’t perfect!

Best of luck to my fellow Android Devs and if you’re interested in this little piece of code, here’s the GitHub link!(be aware, Microsoft inside)