<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>Forem: Kostas Tsalikis</title>
    <description>The latest articles on Forem by Kostas Tsalikis (@tsalikispk).</description>
    <link>https://forem.com/tsalikispk</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F263827%2F81fcae09-a7f4-485a-a35d-373b0f44fa9f.png</url>
      <title>Forem: Kostas Tsalikis</title>
      <link>https://forem.com/tsalikispk</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://forem.com/feed/tsalikispk"/>
    <language>en</language>
    <item>
      <title>A confusing build failure</title>
      <dc:creator>Kostas Tsalikis</dc:creator>
      <pubDate>Wed, 06 Nov 2019 23:00:09 +0000</pubDate>
      <link>https://forem.com/tsalikispk/a-confusing-build-failure-15ml</link>
      <guid>https://forem.com/tsalikispk/a-confusing-build-failure-15ml</guid>
      <description>&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--fzBvGT1O--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://www.droidship.com/images/posts/broken_builds/judge-dredd-under-arrest.jpg" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--fzBvGT1O--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://www.droidship.com/images/posts/broken_builds/judge-dredd-under-arrest.jpg" alt=""&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h5&gt;
  
  
  TL;DR
&lt;/h5&gt;

&lt;ul&gt;
&lt;li&gt;Do not overuse mock test doubles.&lt;/li&gt;
&lt;li&gt;Check the quality of tests in code reviews as well.&lt;/li&gt;
&lt;li&gt;Validate that the build between Android Studio and CI servers is invoked through the same commands.&lt;/li&gt;
&lt;li&gt;Investigate thoroughly build failures and try to have them fixed as soon as possible, before merging.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  A wild failing build appears
&lt;/h2&gt;

&lt;p&gt;Nowadays, it has become quite a common practice to build and check software on machines other than local workstations, most of the time called CI servers(CI stands for &lt;a href="https://martinfowler.com/articles/continuousIntegration.html"&gt;Continuous Integration&lt;/a&gt;). This can be done either manually or automatically, usually triggered by a pull/merge request or a direct push on the main trunk (in git terminology most of the times named &lt;em&gt;master&lt;/em&gt;).&lt;/p&gt;

&lt;p&gt;The point is that there’s a single place where binaries are packaged and code is checked for quality and correctness, so we can merge changes safely and with confidence.&lt;/p&gt;

&lt;p&gt;When a failure appears in a build, it should be investigated why it happened. Did a commit actually break functionality? Were static code analysis checks too harsh and maybe they must be relaxed a little bit? Recently, one of the failures that left me most perplexed was a build where the unit tests failed on the CI server but passed locally! How did this happen? Investigating on this confusing build failure unearthed bigger problems than just a breaking unit test.&lt;/p&gt;

&lt;h2&gt;
  
  
  Mockito cannot mock final classes
&lt;/h2&gt;

&lt;p&gt;So why was the build failing? When the unit tests ran, some of them would fail with an error stating that Mockito (more specifically &lt;a href="https://github.com/nhaarman/mockito-kotlin"&gt;mockito-kotlin&lt;/a&gt;) - a library commonly used in Java and Android to provide mock test doubles for behavior verification - cannot mock final classes.&lt;/p&gt;

&lt;p&gt;In order to understand the error, let’s try to understand first how Mockito works. It creates, at runtime, objects that extend interfaces or classes designed to verify that a set of methods were called with the intended parameters. If a class that is attempted to be mocked is declared as &lt;code&gt;final&lt;/code&gt;, then the error above will be thrown as a final class cannot be extended at compile or run time. In our unit test, a Kotlin class was mocked and as Kotlin classes are by default&lt;code&gt;final&lt;/code&gt;, unless explicitly declared &lt;code&gt;open&lt;/code&gt;, the error above was thrown.&lt;/p&gt;

&lt;p&gt;Although the culprit is found, we still have not figured out why the tests passed locally but failed on the CI server.&lt;/p&gt;

&lt;h2&gt;
  
  
  Maybe Mockito can mock final classes after all
&lt;/h2&gt;

&lt;p&gt;If Mockito cannot mock final classes, then why do local tests pass? Well, sure there must be some way to mock a final class, and that’s exactly what happens when the &lt;code&gt;org.mockito:mockito-inline&lt;/code&gt; dependency is added to the gradle build file.&lt;/p&gt;

&lt;p&gt;The problem is that the failing module did not compile with the dependency above. Instead, a submodule did declare mockito-inline on its &lt;code&gt;build.gradle&lt;/code&gt; but not as a transitive dependency, meaning that final classes could be mocked on that submodule only, not on the top module whose tests were failing.&lt;/p&gt;

&lt;p&gt;This could easily be fixed by either declaring mockito-inline as transitive, or adding it on the top module, but that would not explain why the test resources are compiled differently on the CI server than locally.&lt;/p&gt;

&lt;p&gt;Based on gradle files, on the CI server the build failed as expected, but locally mockito-inline was compiled on the top module (where it shouldn’t) and it wrongfully passed. This, however, begs the following question: how can the CI server be compiled and tested in a different way than the local build?&lt;/p&gt;

&lt;p&gt;It turns out that different commands are employed to compile and test the source code. On the CI server the project is compiled and tested with gradle commands, thus the mockito-inline is not compiled and the test that mocks Kotlin classes fails. On the other hand, the local builds used the test runner that is natively built into Android Studio, which happens to compile all libraries irrespectively of how they are declared on each module’s &lt;code&gt;build.gradle&lt;/code&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  But why did mockito-inline was used on the first place?
&lt;/h2&gt;

&lt;p&gt;At last, the mystery has been solved but let’s dig a little deeper. Why did a test try to mock an otherwise concrete class? And when/why was the mockito-inline dependency introduced first?&lt;/p&gt;

&lt;p&gt;The Kotlin class was mocked just as a filler object for the constructor. No verifications were performed on that mocked object - neither was it used to stub a value. Hence, the concrete class should be used as is or in case of an interface, which cannot be instantiated, a dummy test double. If, however, a concrete class was mocked because it was difficult to instantiate (e.g. it has too many dependencies on its constructor), then this is a moment where one needs to pause and think twice. As for value(&lt;code&gt;data&lt;/code&gt;) classes?&lt;/p&gt;

&lt;p&gt;Quoted directly from the book &lt;em&gt;Growing object-oriented Guided by Tests&lt;/em&gt; [&lt;sup id="fnref:1"&gt;1&lt;/sup&gt;]:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;&lt;em&gt;Don’t Mock Values&lt;/em&gt;&lt;/strong&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;On the other hand, mockito-inline was introduced in the submodule in order to verify the behavior of a third-party library. Let’s say that we had to test the persistence layer of an app. We could either run an integrated test in order to check if the code we’ve written works well against the real database, or we could mock the database as below.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight plaintext"&gt;&lt;code&gt;@Test
    public void givenDbIsEmpty_whenInsertData_thenDbSavesTheNewEntry() throws IOException {
        /* DAO: Data Access Object
         * usually referred to an object that fetches 
         * data from a database or other kinds of data source. */
        SomeDAO aDao = new SomeDAO();
        database = mock(ExternalDatabase.class); 
        when(database.select(any())).thenReturn(new SomeDAO());

        database.insert(aDao);

        SomeDAO savedDao = database.select(aDao);
        assertThat(selectedDao, is(equalTo(aDao);
    }
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;First of all, the problem with this test is that it actually tests nothing. The class under test is mocked and its result is stubbed, so it seems all that is tested here is the ability of the mock framework to stub a value. These kinds of tests give us no feedback and no confidence, in other words they provide zero value. We should instead automate the test for the real thing or test it manually.&lt;/p&gt;

&lt;p&gt;What’s more, we are not listening to the tests. Instead of trying to guess how the library should respond to a request and find ways to mock/stub whatever is required to feed that answer to an assertion, we should add an Adapter layer over the third-party code, test the Adapter with the library and mock callbacks that we may pass to the Adapter layer.&lt;/p&gt;

&lt;p&gt;Perhaps some direct quotes can paint the picture in a better way [&lt;sup id="fnref:2"&gt;2&lt;/sup&gt;]:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;The mess in such tests is telling us that the design isn’t right but, instead of fixing the problem by improving the code, we have to carry the extra complexity in both code and test.&lt;/p&gt;

&lt;p&gt;A second risk is that we have to be sure that the behavior we stub or mock matches what the external library will actually do.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h2&gt;
  
  
  Mitigate the many faces of the problem
&lt;/h2&gt;

&lt;p&gt;So far we’ve seen that there is a build failure that was only caught on the CI server caused by the abuse of mocks on unit tests and the difference in the way CI and local builds are created. Moreover, the failure managed to pass to the main trunk and obstruct other pull requests even though no bugs were introduced. Is there a single root cause in this situation? Multiple layers of safety had to be overridden in order for the failure to reach the mainline.&lt;/p&gt;

&lt;p&gt;This is not so much an issue of technical deficiency - all developers on the team are quite competent. In order to understand the problems and their various causes, let’s state the facts and try to analyze the situation.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;Mocks are used excessively and on the wrong context&lt;/em&gt;&lt;/strong&gt;. They are a special case of test doubles that are used for verification testing [&lt;sup id="fnref:3"&gt;3&lt;/sup&gt;].&lt;/p&gt;

&lt;p&gt;Using mocks as the de facto test double highlights a lack of understanding of the tools used for testing. Quoting again Nat Pryce and Steve Freeman [&lt;sup id="fnref:1"&gt;1&lt;/sup&gt;]:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;our intention in test-driven development is to use mock objects to bring out relationships between objects.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;In every test, it should be carefully evaluated what kind of test doubles (if any) are required and try to minimize mocks only for verifying behavior on interfaces. Of course, there are times where every rule needs to be broken, but most of times we can avoid using tools such as mockito-inline and PowerMock.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;The build failed too late and only on the CI server&lt;/em&gt;&lt;/strong&gt;. The local workstations and the CI server should build with the same commands in order to avoid unpleasant surprises like this one. Unfortunately, it may be a common assumption that Android Studio builds and tests the same way with the setup of a CI server(this surely caught me by surprise as well).&lt;/p&gt;

&lt;p&gt;Maybe we could check once in a while the way Android Studio builds because an update can change how things are built and tested.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;Broken code passed on the main trunk&lt;/em&gt;&lt;/strong&gt;. Even though the build failed, eventually the code was merged and made available for others.&lt;/p&gt;

&lt;p&gt;The safety nets here could be more thorough code reviews that check the quality of the tests as well.&lt;/p&gt;

&lt;h2&gt;
  
  
  Summing up
&lt;/h2&gt;

&lt;p&gt;Sometimes being in a hurry does not help and if the CI server is erratic and fails often from timeouts, we may think that it’s a fault negative. In any case, we should always investigate why builds fail and try to fix them again as soon as possible. Just having tests is not enough - they should provide fast feedback and confidence. They should be fast, deterministic, easy to read and understand, easy to set up and their failures clear to diagnose. These qualities of tests are the weapons that a developer can exploit in order to refactor aggressively and keep the system easy to understand and change. Add critical thinking to the mix in order to listen to what tests are trying to tell us about our design and we have the ingredients to battle complexity.&lt;/p&gt;

&lt;p&gt;This may sound a little provocative, but we could as well delete tests that do not adhere to the qualities above as we end up with double the burden of maintenance and confusion.&lt;/p&gt;

&lt;p&gt;As a personal critique on my part, I could probably say that when I was tasked to provide guidelines to the team about verification testing, I felt that I should have emphasized even more on the dangers of mocking too much. After all one cannot learn just by one example, especially from code that is not created with testing in mind - meaning there will be cut corners and “broken” rules on these examples.&lt;/p&gt;

&lt;p&gt;Finally, this can be seen as a further proof that tools by themselves do not solve problems. Having tests and a CI server is not enough. It is critical to have a deep understanding why these set of techniques and tools are used, as well as the right place and way to use them. Fortunately, this level of understanding is not the result of arcane magic but can be acquired through repetitive practice and retrospection. We are bound to fail through inexperience but bound to succeed through curiosity and will to learn.&lt;/p&gt;

&lt;p&gt;Special and many thanks to &lt;em&gt;&lt;a href="https://twitter.com/ktsiligkos"&gt;Kleomenis Tsiligkos&lt;/a&gt;&lt;/em&gt; and &lt;em&gt;&lt;a href="https://www.linkedin.com/in/michalis-romanos-kolozoff-03b19180/"&gt;Michalis Kolozoff&lt;/a&gt;&lt;/em&gt; for proof reading.&lt;/p&gt;




&lt;ol&gt;
&lt;li&gt;Nat Pryce - Steve Freeman: Growing object-oriented Guided by Tests, &lt;em&gt;Chapter 20: Listening to the tests&lt;/em&gt;&lt;sup&gt;[return]&lt;/sup&gt;
&lt;/li&gt;
&lt;li&gt;Nat Pryce - Steve Freeman: Growing object oriented Guided by Tests, &lt;em&gt;Chapter 8: Building on Third-Party Code&lt;/em&gt;&lt;sup&gt;[return]&lt;/sup&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://martinfowler.com/articles/mocksArentStubs.html"&gt;Martin Fowler: Mocks aren’t Stubs&lt;/a&gt;&lt;sup&gt;[return]&lt;/sup&gt;
&lt;/li&gt;
&lt;/ol&gt;

</description>
      <category>testing</category>
      <category>android</category>
      <category>ci</category>
    </item>
    <item>
      <title>Uploading an Android library on JCenter</title>
      <dc:creator>Kostas Tsalikis</dc:creator>
      <pubDate>Tue, 21 May 2019 19:47:02 +0000</pubDate>
      <link>https://forem.com/tsalikispk/uploading-an-android-library-on-jcenter-2ddf</link>
      <guid>https://forem.com/tsalikispk/uploading-an-android-library-on-jcenter-2ddf</guid>
      <description>&lt;p&gt;Facing a lack of inspiration for quite some time I decided to draw some from an old project of mine. A couple of years ago I created an open-source library named &lt;a href="https://github.com/tsalik/target-layout"&gt;&lt;code&gt;target-layout&lt;/code&gt;&lt;/a&gt; which was basically a &lt;code&gt;FrameLayout&lt;/code&gt; that draws a view on its center and some &lt;code&gt;drawables&lt;/code&gt; around it, letting the user pinch zoom on the view and select through a range of levels.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--dnbbU7yX--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_66%2Cw_880/https://www.droidship.com/gifs/targetlayout.gif" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--dnbbU7yX--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_66%2Cw_880/https://www.droidship.com/gifs/targetlayout.gif" alt="TargetLayout animation"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Of course a GIF might be the best way to showcase what the library does.&lt;/p&gt;

&lt;p&gt;Apart from the joy of creating a custom and unique UI and delving into the depths of how a view is measured, laid-out and drawn I decided to learn how to publish the library on JCenter. Unfortunately, I haven’t been the world’s best maintainer, so I left the library targeting old Android SDK versions, without any support for AndroidX. What’s more, I had left the project without Continuous Integration (CI from now on) and as the years passed, I forgot how publishing on JCenter works, so I decided to revisit these topics before doing any further work with the library itself.&lt;/p&gt;

&lt;h1&gt;
  
  
  Adding CI on your open-source library
&lt;/h1&gt;

&lt;p&gt;The first think I had to do was updating all its outdated dependencies. This meant updating gradle versions along with target and compile Android SDK versions so any new users of the library would be able to compile it with no problems and warnings. Even though I am the maintainer and could push directly to the master branch, I decided to go for a pull request process with myself. Doing so meant that I would emulate the process of someone else trying to use and modify the library, so I needed to add some checks from an external CI server in order to verify that the library actually builds.&lt;/p&gt;

&lt;p&gt;Among the most usual CI services that support open-source projects and are Android friendly are &lt;a href="https://circleci.com/"&gt;CircleCI&lt;/a&gt; and &lt;a href="https://travis-ci.org/"&gt;TravisCI&lt;/a&gt;. As I had some previous experience with TravisCI on a toy project, I decided to use TravisCI in order to kick-start the process of making the library modernized. In order to start using TravisCI. First of all, it is needed to create an account or sign in with your GitHub account. After doing so, we can add from the dashboard a git repository and then add a &lt;code&gt;.travis.yml&lt;/code&gt; file on the root of the repo. The &lt;code&gt;.travis.yml&lt;/code&gt; is essential as it instructs TravisCI on how to build the project - if TravisCI does not find the &lt;code&gt;.travis.yml&lt;/code&gt; on the root of the repo it will be unable to build. Below you can find a sample &lt;code&gt;.travis.yml&lt;/code&gt; for building an Android project:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;language: android
jdk: oraclejdk8

before_cache:
  - rm -f $HOME/.gradle/caches/modules-2/modules-2.lock
  - rm -fr $HOME/.gradle/caches/*/plugin-resolution/

cache:
  directories:
    - $HOME/.gradle/caches/
    - $HOME/.gradle/wrapper/

env:
  global:
    - ANDROID_API=28
    - ANDROID_BUILD_TOOLS=28.0.3

android:
  components:
    - tools
    - platform-tools
    - build-tools-$ANDROID_BUILD_TOOLS
    - android-$ANDROID_API
    - extra-google-m2repository
    - extra-android-m2repository # for design library

licenses:
  - android-sdk-preview-license-.+
  - android-sdk-license-.+
  - google-gdk-license-.+

before_install:
  - mkdir "$ANDROID_HOME/licenses" || true
  - echo -e "\n8933bad161af4178b1185d1a37fbf41ea5269c55" &amp;gt; "$ANDROID_HOME/licenses/android-sdk-license"
  - echo -e "\n84831b9409646a918e30573bab4c9c91346d8abd" &amp;gt; "$ANDROID_HOME/licenses/android-sdk-preview-license"
  - yes | $ANDROID_HOME/tools/bin/sdkmanager "build-tools;24.0.3"
  - chmod +x gradlew

script:
  - "./gradlew :library_module_name:clean :library_module_name:build"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Explaining the .travis.yml
&lt;/h2&gt;

&lt;p&gt;The yml above instructs the CI service to clear the caches before building and exports as environment variables the desired Android API and build tools versions. We then declare which components we will use, along with their licenses. This is something that, in our daily work life, do through Android Studio manually but since we are building on a CI server, we need to do this programmatically. By declaring them this way on the &lt;code&gt;.travis.yml&lt;/code&gt; we are instructing TravisCI to download the desired components and accept any of the licenses needed. As there are some problems with accepting the licenses, we additionally instruct to accept the licenses through the &lt;code&gt;sdkmanager&lt;/code&gt; tool and finally make the &lt;code&gt;gradlew&lt;/code&gt; file executable in order to let TravisCI execute the gradle scripts for building the project. Finally the &lt;code&gt;script&lt;/code&gt; section is where the build actually happens. Since we are only interested in building the library module and not the sample that accompanies it, we only clean and build the library module(on the script with a name exampled as library_module_name)&lt;/p&gt;

&lt;h2&gt;
  
  
  Some pain points
&lt;/h2&gt;

&lt;p&gt;We must be sure that we have added the &lt;code&gt;.travis.yml&lt;/code&gt; on the root of the git directory as otherwise TravisCI will not be able to build. Another pain point is the licenses. Accepting them through the &lt;code&gt;sdkmanager&lt;/code&gt; solves any persisting problems. Unfortunately I did not find a way to access the lint html report on TravisCI, so I ended up showing any reports as text on the console through the &lt;code&gt;build.gradle&lt;/code&gt; of the library module.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;android {
    compileSdkVersion 28
    buildToolsVersion "28.0.3"

    lintOptions {
        textReport true
        abortOnError true
        warningsAsErrors false
    }
    ...
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h1&gt;
  
  
  Updating gradle versions and moving on AndroidX
&lt;/h1&gt;

&lt;p&gt;At this point we have a build that passes through TravisCI and we are ready to update gradle and Android SDK versions. Fortunately this is done easily through Android Studio since it already gives warnings on the library’s &lt;code&gt;build.gradle&lt;/code&gt; file. Just hitting &lt;code&gt;Alt+Enter&lt;/code&gt; on the respective versions, updates them automatically and the migration tool for AndroidX works fine as the project does not have any dependencies apart from the Android &lt;code&gt;appcompat&lt;/code&gt; library - so I didn’t have to deal with any of the &lt;a href="https://www.droidship.com/posts/androidx"&gt;problems of the AndroidX migration&lt;/a&gt;. Now we are ready to create the pull request, see it pass the TravisCI build and safely accept it. What’s more we can add the TravisCI build badge in our &lt;code&gt;README.md&lt;/code&gt; to showcase that the build is passing.&lt;/p&gt;

&lt;h1&gt;
  
  
  Uploading on JCenter
&lt;/h1&gt;

&lt;p&gt;Now that the build passes, we are finally ready to upload the library’s artifacts on JCenter so everyone will be able to add it as a dependency on their builds. But before uploading anything anywhere, first we need to know what files to actually upload!&lt;/p&gt;

&lt;h2&gt;
  
  
  The maven repository
&lt;/h2&gt;

&lt;p&gt;For our library to be traceable and downloadable we need to upload it on a maven repository. A very good and thorough explanation of what a maven repository is and how it works can be found &lt;a href="https://blog.packagecloud.io/eng/2017/03/09/how-does-a-maven-repository-work/#what-is-a-maven-dependency"&gt;here&lt;/a&gt;. In a few words, a maven repository is a directory where all the library’s executable files are stored and are available to download. The path of the directory is determined by the library’s &lt;code&gt;.pom&lt;/code&gt; file, which essentially gives the library its name as well and adds any transitive dependencies that it has. The &lt;code&gt;.pom&lt;/code&gt; file for the &lt;code&gt;target-layout&lt;/code&gt; library that serves as an example for this post is the following:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;?xml version="1.0" encoding="UTF-8"?&amp;gt;
&amp;lt;project xmlns="http://maven.apache.org/POM/4.0.0" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"&amp;gt;
  &amp;lt;modelVersion&amp;gt;4.0.0&amp;lt;/modelVersion&amp;gt;
  &amp;lt;groupId&amp;gt;com.tsalik.targetlayout&amp;lt;/groupId&amp;gt;
  &amp;lt;artifactId&amp;gt;targetlayout&amp;lt;/artifactId&amp;gt;
  &amp;lt;version&amp;gt;1.0.2&amp;lt;/version&amp;gt;
  &amp;lt;packaging&amp;gt;aar&amp;lt;/packaging&amp;gt;
  &amp;lt;dependencies&amp;gt;
    &amp;lt;dependency&amp;gt;
      &amp;lt;groupId&amp;gt;androidx.appcompat&amp;lt;/groupId&amp;gt;
      &amp;lt;artifactId&amp;gt;appcompat&amp;lt;/artifactId&amp;gt;
      &amp;lt;version&amp;gt;1.0.2&amp;lt;/version&amp;gt;
      &amp;lt;scope&amp;gt;runtime&amp;lt;/scope&amp;gt;
    &amp;lt;/dependency&amp;gt;
  &amp;lt;/dependencies&amp;gt;
&amp;lt;/project&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The above means, would anyone like to fetch the library from a maven repository with gradle, they would have to add in the dependencies of their &lt;code&gt;build.gradle&lt;/code&gt; file the following line:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;implementation "com.tsalik.targetlayout:targetlayout:1.0.2"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Since this is an Android library, it is declared that an &lt;code&gt;.aar&lt;/code&gt;(named targetlayout-1.0.2.aar more specifically) file should be downloaded, along with the dependencies of the library, which is the &lt;code&gt;androidx.appcompat:appcompat:1.0.2&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Now we know that we need to produce the &lt;code&gt;.aar&lt;/code&gt; from the code of the library and add it along with a &lt;code&gt;.pom&lt;/code&gt; file, including any extra resources or javadoc on a maven repository, so next steps should be about building the library and adding any of the artifacts above on a specific maven repository (in our case we want to eventually upload it on the JCenter repository)&lt;/p&gt;

&lt;h2&gt;
  
  
  Let’s build and publish locally
&lt;/h2&gt;

&lt;p&gt;First of all, we need to create the artifacts mentioned above on a local repository. To do this we need to know how to publish a maven repository through gradle, which is the de facto tool for building on Android (although alternatives like &lt;a href="https://bazel.build/"&gt;Bazel&lt;/a&gt; and &lt;a href="https://buck.build/"&gt;Buck&lt;/a&gt; do exist). An extensive documentation on how maven publishing works can be found &lt;a href="https://docs.gradle.org/current/userguide/publishing_maven.html"&gt;here&lt;/a&gt;(at the time of writing for the 5.4.1 version of gradle). Although the official gradle documentation describes how publishing works the &lt;a href="https://github.com/bintray/gradle-bintray-plugin"&gt;bintray plugin documentation&lt;/a&gt;(version 1.8.4 at the time of writing) is more specific on how to publish specifically in Android and avoid common pitfalls.&lt;/p&gt;

&lt;p&gt;Below you can find the example gradle script for publishing the &lt;code&gt;target-layout&lt;/code&gt; library:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;apply plugin: 'maven-publish'

task androidJavadocs(type: Javadoc) {
    failOnError = false
    source = android.sourceSets.main.java.srcDirs
    ext.androidJar = "${android.sdkDirectory}/platforms/${android.compileSdkVersion}/android.jar"
    classpath += files(ext.androidJar)
    exclude ' **/R.html', '** /R.*.html', '**/index.html'
}

task androidJavadocsJar(type: Jar, dependsOn: androidJavadocs) {
    classifier = 'javadoc'
    from androidJavadocs.destinationDir
}

task androidSourcesJar(type: Jar) {
    classifier = 'sources'
    from android.sourceSets.main.java.srcDirs
}

project.afterEvaluate {
    publishing {
        publications {
            targetlayout(MavenPublication) {
                groupId project.ext.PUBLISH_GROUP_ID
                artifactId project.ext.PUBLISH_ARTIFACT_ID
                version project.ext.PUBLISH_VERSION

                artifact bundleReleaseAar
                artifact androidJavadocsJar
                artifact androidSourcesJar

                pom.withXml {
                    final dependenciesNode = asNode().appendNode('dependencies')

                    ext.addDependency = { Dependency dep, String scope -&amp;gt;
                        if (dep.group == null || dep.version == null || dep.name == null || dep.name == "unspecified")
                            return // ignore invalid dependencies

                        final dependencyNode = dependenciesNode.appendNode('dependency')
                        dependencyNode.appendNode('groupId', dep.group)
                        dependencyNode.appendNode('artifactId', dep.name)
                        dependencyNode.appendNode('version', dep.version)
                        dependencyNode.appendNode('scope', scope)

                        if (!dep.transitive) {
                            // If this dependency is transitive, we should force exclude all its dependencies them from the POM
                            final exclusionNode = dependencyNode.appendNode('exclusions').appendNode('exclusion')
                            exclusionNode.appendNode('groupId', '*')
                            exclusionNode.appendNode('artifactId', '*')
                        } else if (!dep.properties.excludeRules.empty) {
                            // Otherwise add specified exclude rules
                            final exclusionNode = dependencyNode.appendNode('exclusions').appendNode('exclusion')
                            dep.properties.excludeRules.each { ExcludeRule rule -&amp;gt;
                                exclusionNode.appendNode('groupId', rule.group ?: '*')
                                exclusionNode.appendNode('artifactId', rule.module ?: '*')
                            }
                        }
                    }

                    // List all "compile" dependencies (for old Gradle)
                    configurations.compile.getDependencies().each { dep -&amp;gt; addDependency(dep, "compile") }
                    // List all "api" dependencies (for new Gradle) as "compile" dependencies
                    configurations.api.getDependencies().each { dep -&amp;gt; addDependency(dep, "compile") }
                    // List all "implementation" dependencies (for new Gradle) as "runtime" dependencies
                    configurations.implementation.getDependencies().each { dep -&amp;gt; addDependency(dep, "runtime") }
                }
            }
        }

        repositories {
            maven {
                // change to point to your repo, e.g. http://my.org/repo
                url = "$buildDir/repo"
            }
        }
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Although it seems daunting, let’s try to dissect it. First of all, we declare our own tasks for generating Javadoc and Android resources on their respective jars. The &lt;code&gt;publishing&lt;/code&gt; and &lt;code&gt;publication&lt;/code&gt; closures are from the &lt;code&gt;maven-publish&lt;/code&gt; plugin, which we must apply on top of the script. Inside the &lt;code&gt;publication&lt;/code&gt; closure we declare a maven publication named &lt;code&gt;targetlayout&lt;/code&gt; - named after the library (for your own library you must apply an appropriate name).&lt;/p&gt;

&lt;p&gt;Continuing inside the &lt;code&gt;publication&lt;/code&gt; closure, we apply the &lt;code&gt;groupdId&lt;/code&gt;, &lt;code&gt;artifactId&lt;/code&gt; and &lt;code&gt;version&lt;/code&gt; in order to name the library appropriately. The values on the example above are set as extra project properties on the &lt;code&gt;build.gradle&lt;/code&gt; file of the library’s module so that we can reference them in one single point. Then we declare which artifacts (i.e. files) we need the publication to have. We want the &lt;code&gt;.aar&lt;/code&gt; for the release build, as well as the Javadoc and any extra resources as jars (we do so by calling the tasks we declared above).&lt;/p&gt;

&lt;p&gt;Finally, we manually add all the dependencies of the library for &lt;code&gt;compile&lt;/code&gt;, &lt;code&gt;api&lt;/code&gt; and &lt;code&gt;implementation&lt;/code&gt; configurations, as otherwise it will not be done automatically (the bintray-gradle-plugin explains nicely why).&lt;/p&gt;

&lt;p&gt;In order to check if all this configuration for the publication works, we can add the &lt;code&gt;repositories&lt;/code&gt; closure and publish on a local directory (in this case a directory named repo under the library module’s build folder). Now in order to test that everything is fine we can execute:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;./gradlew clean :targetlayout:publish
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;and we should be able to check that all the artifacts(aar, javadoc, pom files) have been published on the build folder and the pom has the right &lt;code&gt;groupId&lt;/code&gt;, &lt;code&gt;artifactId&lt;/code&gt; and &lt;code&gt;version&lt;/code&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  So where should we upload then?
&lt;/h2&gt;

&lt;p&gt;Now that we have seen how a publication works and what files it contains, we are ready to finally upload the library on a maven repository other than the local one that we created. Among the various public maven repositories that exist, the more popular ones for Android development are Maven Central, JCenter and JitPack. A comparison between them is out of the scope of this post and since I had already uploaded the library on JCenter, we will focus only on uploading there. Fortunately, there already exists a gradle plugin for uploading on JCenter so there will be no need to re-invent the wheel.&lt;/p&gt;

&lt;p&gt;In order to install the bintray gradle plugin, we apply the &lt;code&gt;classpath 'com.jfrog.bintray.gradle:gradle-bintray-plugin:1.8.4'&lt;/code&gt; on the dependencies of the top &lt;code&gt;build.gradle&lt;/code&gt; of the project and then apply it on the same script declared above(which is responsible for publishing).&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;apply plugin: 'maven-publish'
apply plugin: 'com.jfrog.bintray'

...
project.afterEvaluate {
    publishing {
        publications {
            targetlayout(MavenPublication) {
                ...
            }
        }
    }

    bintray {
            Properties localProperties = new Properties()
            if (project.rootProject.file('local.properties').exists()) {
                localProperties.load(project.rootProject.file('local.properties').newDataInputStream())
            }
            user = localProperties.getProperty("bintray.user")
            key = localProperties.getProperty("bintray.apikey")
            pkg {
                repo = 'target-layout'
                name = 'target-layout'
                licenses = ['MIT']
                vcsUrl = 'https://github.com/tsalik/target-layout.git'
                version {
                    name = "1.0.2"
                    released = new Date()
                }
            }
            publications = ['targetlayout']
        }
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;There are a couple of things to notice here. First of all, we must have already been singed in JCenter and created a maven repository. I will leave this part out and provide references on how to do it. You can check that the repository and the name of the library have the same name - &lt;code&gt;target-layout&lt;/code&gt;. This is not something mandatory, it just happened at the time I was creating the repository.&lt;/p&gt;

&lt;p&gt;In order to be able to upload the artifact of the publishing, we must somehow authorize ourselves with bintray. The &lt;code&gt;user&lt;/code&gt; and &lt;code&gt;key&lt;/code&gt; fields just do that - but be aware. We &lt;strong&gt;MUST NOT&lt;/strong&gt; add these values on version control as everyone could check these values and upload anything, they want on your maven repository. We can add them as environment variables if we publish and upload through the CI server, or add them on &lt;code&gt;local.properties&lt;/code&gt;(which &lt;strong&gt;MUST&lt;/strong&gt; be on the &lt;code&gt;.gitignore&lt;/code&gt;).&lt;/p&gt;

&lt;p&gt;If you decide to inject them through the &lt;code&gt;local.properties&lt;/code&gt;, make sure that you check that the file exists - in a CI server it will not and the build will fail.&lt;/p&gt;

&lt;p&gt;Note that although I have declared the version as an external property, instead of referencing it I have hardcoded it. I’m sure on the future there will be some frustration with my past self unless I fix it soon 😅.&lt;/p&gt;

&lt;p&gt;Finally, after adding any required metadata, we declare which publications we want to upload. This must be the same value with the name that we declared on the publishing section. At last we are ready to publish the library from the command-line:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;./gradlew clean :targetlayout:bintrayUpload
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h1&gt;
  
  
  Final thoughts
&lt;/h1&gt;

&lt;p&gt;Ultimately revisiting how to add CI on an open-source project and automating its publishing process proved to be a good exercise. Apart from the frustration of some (a lot) broken builds due to misconfigurations on the &lt;code&gt;travis.yml&lt;/code&gt; for setting up CI it was an overall enjoyable ride. Having to deal with how a publication works, clarified a lot of things on how maven works and highlighted that creating a publication with its artifacts and uploading it on a public maven repo are actually two different and partially unrelated things.&lt;/p&gt;

&lt;p&gt;Just publishing locally would have been enough as I would be able to manually upload the artifacts as I did in the past, but this time instead of being dependent on someone else’s ready-made solution, I decided to actually check out how to do this without the help of a third-party plugin. After all, the lesser the plugins the lesser the pain of building a library or app. The bintray plugin was indeed invaluable as it made easy the upload part of publishing the library.&lt;/p&gt;

&lt;h1&gt;
  
  
  Next Steps
&lt;/h1&gt;

&lt;p&gt;Now that the library is updated with the latest gradle and Android SDK versions I can investigate more thoroughly some lint checks and maybe consider adding some animations when the layout first attaches on the window. It is amazing that what used to be on the brink of deprecation now has a new spark and gave inspiration to investigate a variety of things. Another step for future work is to add gpg signing and push the library on Maven Central as well.&lt;/p&gt;

&lt;h1&gt;
  
  
  References
&lt;/h1&gt;

&lt;p&gt;Although there are a lot of posts that cover the publication that have far more detail on how to setup your TravisCI account and how to create an account and the repository on &lt;a href="https://bintray.com/bintray/jcenter"&gt;JCenter&lt;/a&gt; I decided to cover more in depth on how a publication works on a maven repository.&lt;/p&gt;

&lt;p&gt;What’s more, most of the posts used other gradle plugins for the publishing part on top of gradle’s &lt;code&gt;maven-plugin&lt;/code&gt; and since the scope of the exercise was to check how it works with minimal dependencies, I decided to depend only on what’s vanilla on gradle.&lt;/p&gt;

&lt;p&gt;The posts from &lt;a href="https://medium.com/@anitaa_1990/6-easy-steps-to-upload-your-android-library-to-bintray-jcenter-59e6030c8890"&gt;Anitaa Murthy&lt;/a&gt;, &lt;a href="https://medium.com/@yegor_zatsepin/simple-way-to-publish-your-android-library-to-jcenter-d1e145bacf13"&gt;Yegor Zatsepin&lt;/a&gt; and &lt;a href="https://android.jlelse.eu/publishing-your-android-kotlin-or-java-library-to-jcenter-from-android-studio-1b24977fe450"&gt;Wajahat Karim&lt;/a&gt; acted as guides for this one, with excellent replication steps on how to set up the repository on JCenter.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Special thanks to Michalis Kolozoff for proofreading&lt;/em&gt;&lt;/p&gt;

</description>
      <category>android</category>
    </item>
    <item>
      <title>Kotlin puzzles</title>
      <dc:creator>Kostas Tsalikis</dc:creator>
      <pubDate>Sun, 27 Jan 2019 20:55:38 +0000</pubDate>
      <link>https://forem.com/tsalikispk/kotlin-puzzles-25hf</link>
      <guid>https://forem.com/tsalikispk/kotlin-puzzles-25hf</guid>
      <description>&lt;h1&gt;
  
  
  Some context before the puzzles
&lt;/h1&gt;

&lt;p&gt;One of the books that I’ve be meaning to finish is &lt;em&gt;Growing Object-Oriented Guided by Tests&lt;/em&gt; written by Steve Freeman and Nat Pryce. In their excellent book the authors not only describe how to use tests in order to drive the design of a system but also provide a comprehensive example where they showcase in practice what they preach.&lt;/p&gt;

&lt;p&gt;The example is a Swing application which receives and sends events to a XMPP(a publish/subscribe protocol) server and uses some dated testing libraries(Windowlicker for testing the Swing GUI and JMock for testing with mocks). Even though all code is in Java, I decided to minimize the use of Kotlin in order to focus on the techniques the authors provide and added Mockito instead of JMock for testing mocks. Finally, I ended up with a mixed codebase with most parts written in Java, adding some minimal Kotlin flavor in four cases:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;code&gt;data&lt;/code&gt; classes to replace the use of Apache’s commons equals/hashcode for creating immutable objects.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;sealed&lt;/code&gt; classes instead of &lt;code&gt;enums&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;more idiomatic Kotlin features like &lt;code&gt;map&lt;/code&gt; to replace &lt;code&gt;for&lt;/code&gt; loops.&lt;/li&gt;
&lt;li&gt;computed properties instead of functions inside some Kotlin code.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;In general I wanted to avoid extensive use of Kotlin in order to avoid unpleasant surprises and yet surprises happened, particularly in numbers 3 and 4 from the list above.&lt;/p&gt;

&lt;h1&gt;
  
  
  Puzzle Number 1: a problem with split
&lt;/h1&gt;

&lt;p&gt;In their example, the authors have a class which parses a CSV like response from the network. The response looks something like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;"Event: PRICE; Price: 100; Increment: 20; Bidder: Someone;"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;and they parse the response with the snippet of code below:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;private Map&amp;lt;String, String&amp;gt; unpackEventFrom(Message message) {
        Map&amp;lt;String, String&amp;gt; event = new HashMap&amp;lt;&amp;gt;();
        for (String element : message.getBody().split(";")) {
            String[] pair = element.split(":");
            event.put(pair[0].trim(), pair[1].trim());
        }
        return event;
    }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In this snippet, they just split the string first on &lt;code&gt;;&lt;/code&gt; and then create pairs with splitting &lt;code&gt;:&lt;/code&gt; finally they put keys and values in a map, pretty straightforward. This kind of code is something that could use some Kotlin flavor, so lets rephrase it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;messageBody.split(";")
        .associateTo(auctionEvent.fields) {
                val pair = it.split(":")
                pair[0].trim() to pair[1].trim()
        }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The Kotlin snippet splits the message on &lt;code&gt;;&lt;/code&gt; then creates a pair by splitting on &lt;code&gt;:&lt;/code&gt; and associates the pair to an empty map(the &lt;code&gt;auctions.fields&lt;/code&gt; val that is omitted for brevity). The code was written in Java first, the tests passed but a surprise was there when I converter it to Kotlin, and specifically an &lt;code&gt;IndexOutOfBounds&lt;/code&gt; one! How oh how did this happen? It seems that Kotlin’s &lt;code&gt;split&lt;/code&gt; function has a different implementation than Java. Something that I was not aware of is that Java’s split also has a &lt;code&gt;limit&lt;/code&gt; parameter, and when calling &lt;code&gt;split(;)&lt;/code&gt; this actually calls &lt;code&gt;split(;, 0)&lt;/code&gt;. Koltin does also the same but the difference is how &lt;strong&gt;zero&lt;/strong&gt; is interpreted on the two languages.&lt;/p&gt;

&lt;p&gt;Quoted directly from Java’s documentation:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;If limit is zero then the pattern will be applied as many times as possible, the array can have any length, &lt;strong&gt;and trailing empty strings will be discarded&lt;/strong&gt;.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;We can see that Java applies an extra meaning to the &lt;code&gt;limit&lt;/code&gt; parameter. On the contrary, Kotlin let’s the user apply only non-negative limits and does not discard the trailing empty spaces, unless you explicitely tell it to do.&lt;/p&gt;

&lt;p&gt;The exact equivalent in Kotlin would be something like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;messageBody.split(";")
        .dropLastWhile { it.isEmpty() }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Why would Kotlin’s creators do something like this? One could argue that Java is the one which is wrong here, since the limit parameter is not only specifying the number of times that a delimiter should apply, but also adds a different meaning that is completely irrelevant and treats zero like a special value. Another nice explanation of why Kotlin’s &lt;code&gt;split&lt;/code&gt; is different from the Java one can be found on &lt;a href="https://stackoverflow.com/questions/48697300/difference-between-kotlin-and-java-string-split-with-regex"&gt;this stackoverflow answer&lt;/a&gt;.&lt;/p&gt;

&lt;h1&gt;
  
  
  Puzzle Number 2: This is not the (computed) property you’re looking for
&lt;/h1&gt;

&lt;p&gt;The snippet with the parsing was from an Event class. The authors of the example decided not to expose the map but instead create methods in order to expose the values of an Event.The &lt;code&gt;unpack&lt;/code&gt; method from above acted as a Factory Method and initialized the map and the various methods exposed the values of the event. In my Kotlin flavored Event I created a companion object and private constructor to emulate the Factory method and decided to use computed properties. At first I tried something like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;class Event private constructor() {

        private val fields = mutableMapOf&amp;lt;String, String&amp;gt;()

        val type = parse("Event")

        private fun parse(key: String) = fields.get(key)!!

        companion object {
            fun from(message: Message): Event {
                val auctionEvent = Event()
                messageBody.split(";")
                    .dropLastWhile { it.isEmpty() }
                    .associateTo(auctionEvent.fields) {
                        val pair = it.split(":")
                        pair[0].trim() to pair[1].trim()
                    }
                return auctionEvent
            }
        }
    }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Alas, I could not be more wrong on thinking that the property &lt;code&gt;type&lt;/code&gt; would actually parse the key from the map after the map was populated with values on the &lt;code&gt;from&lt;/code&gt; function. Since the Event is created before populating the map, the &lt;code&gt;type&lt;/code&gt; property will parse immediately the key from the map, and since the map will be empty on construction time, the value will be null and a glorious &lt;code&gt;kotlin.KotlinNullPointerException&lt;/code&gt; will be thrown, as the parse method gets the key with the not null&lt;code&gt;!!&lt;/code&gt; operator. The &lt;code&gt;type&lt;/code&gt; field seems as a computed property, but it actually is not, it should obviously be declared as below:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;val type
        get() = parse("Event")
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Even though this surprise was entirely my own fault it got me thinking that maybe it would be better to eventually declare a function instead of a computed property. The use of computed properties surely is a more idiomatic use of Kotlin, but on the other hand I feel like a property should act as the state of the object and in this example the state of the object is the map and we just expose its values on transformations of the values of the map, which should be exposed functions. Of course I’m not advocating against the use of computed properties, this is just a rant from a personal failure.&lt;/p&gt;

&lt;h1&gt;
  
  
  Final thoughts
&lt;/h1&gt;

&lt;p&gt;As we can see, even when we try to minimize the use of idiomatic Kotlin or just try to port Java code to Kotlin, easy mistakes can be made. Of course this can happen whenever we’re trying to learn a new language but porting Java to Kotlin is more devious, as even though the two languages seem to have similar API they can actually differ on their implementation. Caution is needed, but in the example that I presented I happened to be lucky as the use of TDD provided a nice regression suite that caught my faults immediately - and indeed they were my own faults as I made assumptions on the APIs and idioms without checking Kotlin’s documentation first!&lt;/p&gt;

&lt;p&gt;Photo by &lt;a href="https://unsplash.com/@momentsbygabriel"&gt;Gabriel Crismariu&lt;/a&gt; on &lt;a href="https://unsplash.com/"&gt;Unsplash&lt;/a&gt;&lt;/p&gt;

</description>
      <category>kotlin</category>
    </item>
    <item>
      <title>Git tip: cherry-pick with an -x</title>
      <dc:creator>Kostas Tsalikis</dc:creator>
      <pubDate>Sat, 29 Sep 2018 10:23:36 +0000</pubDate>
      <link>https://forem.com/tsalikispk/git-tip-cherry-pick-with-an-x-5fmc</link>
      <guid>https://forem.com/tsalikispk/git-tip-cherry-pick-with-an-x-5fmc</guid>
      <description>&lt;h3&gt;
  
  
  TL;DR
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;cherry-pick&lt;/code&gt; takes a commit and applies its changes to your current branch.&lt;/li&gt;
&lt;li&gt;When working with others, use &lt;code&gt;-x&lt;/code&gt; option in order to highlight on the commit message that this is cherry-picked and not the original commit.&lt;/li&gt;
&lt;li&gt;Use it sparingly, instead of a &lt;code&gt;merge&lt;/code&gt;, when you need only one specific commit.&lt;/li&gt;
&lt;li&gt;Overusing it can result in confusing history with duplicate commits, thus &lt;code&gt;merge&lt;/code&gt; is generally preferred.&lt;/li&gt;
&lt;/ul&gt;

&lt;h1&gt;
  
  
  What is a cherry-pick?
&lt;/h1&gt;

&lt;p&gt;When cherry-picking you basically take the commit that you’re targeting and apply its changes to your current HEAD. This will lead to a brand new commit with a different SHA and the same commit message.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;git cherry-pick &amp;lt;target commit SHA&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h1&gt;
  
  
  Why cherry-pick in the first place?
&lt;/h1&gt;

&lt;p&gt;Let’s say that you’ve drawn yourself into a corner – you need changes from another branch, but you don’t need &lt;em&gt;all&lt;/em&gt; the changes, just some commits. Here is the only case where &lt;code&gt;cherry-pick&lt;/code&gt; should be applied.&lt;/p&gt;

&lt;h1&gt;
  
  
  Main disadvantages
&lt;/h1&gt;

&lt;p&gt;Most times developers choose to &lt;code&gt;merge&lt;/code&gt; instead of performing a &lt;code&gt;cherry-pick&lt;/code&gt; – but why is that? Well, one must be very careful when applying &lt;code&gt;cherry-pick&lt;/code&gt;, especially with the order that different commits are applied. When merging, you can be sure that the commits are applied with the right order, so you just have to resolve appropriately the conflicts. On the contrary, when dealing with a number of cherry-picks, you must manually find the correct order of the commits and apply them one by one according to their date.&lt;/p&gt;

&lt;p&gt;What’s more, you end up with duplicate commits, since the name of the cherry-picked commit will be the same with the original one.&lt;/p&gt;

&lt;p&gt;So, &lt;code&gt;cherry-pick&lt;/code&gt; is bad because:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;You must manually apply the cherry-picks – depending on the number of commits that you have to apply it may be difficult to find the right order and this is surely an error prone process.&lt;/li&gt;
&lt;li&gt;Duplicate commits result in weird looking and ugly history.&lt;/li&gt;
&lt;li&gt;Let’s say someone else needs that fix in another branch, will they pick the right commit or will they &lt;code&gt;cherry-pick&lt;/code&gt; the &lt;em&gt;cherry-picked&lt;/em&gt; one. After all, the cherry-picked one may have a conflict that you do not need.&lt;/li&gt;
&lt;/ol&gt;

&lt;h1&gt;
  
  
  A contrived example of ugly history.
&lt;/h1&gt;

&lt;p&gt;Below follows a contrived example of how a cherry-pick can make the history look ugly. Let’s say that you create two commits on &lt;em&gt;master&lt;/em&gt;, &lt;em&gt;A&lt;/em&gt; and &lt;em&gt;B&lt;/em&gt;, and at that moment you want to create a new feature branch(named with an extra dose of imagination &lt;em&gt;feature&lt;/em&gt;) and add a new commit &lt;em&gt;C&lt;/em&gt;.&lt;/p&gt;

&lt;p&gt;At the moment we have something like this.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;A --- B &amp;lt;- (master)
          \
           \
            C &amp;lt;- (feature)
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then we go back again to &lt;em&gt;master&lt;/em&gt; and commit &lt;em&gt;D&lt;/em&gt;. We commit &lt;em&gt;E&lt;/em&gt; on &lt;em&gt;feature&lt;/em&gt;, but before that, we would need to apply fix &lt;em&gt;D&lt;/em&gt; from &lt;em&gt;master&lt;/em&gt;, thus we cherry-pick &lt;em&gt;D&lt;/em&gt;.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;   A --- B --- D     &amp;lt;- (master)
          \
           \
            C --- D' --- E     &amp;lt;- (feature)
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;At this point, we would like to merge the &lt;em&gt;feature&lt;/em&gt; back to &lt;em&gt;master&lt;/em&gt;. Now the graph would seem something like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;A --- B --- D ----- Merge Commit     &amp;lt;- (master)
          \                /
           \              /
            C --- D' --- E     &amp;lt;- (feature)
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And a &lt;code&gt;git log --oneline&lt;/code&gt; would show us the duplicate commits:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;5b5f739 (HEAD -&amp;gt; master) Merge branch 'feature'
d5c76ad E
52ed367 D
c097b61 D
af599fa C
383a1e1 B
c1fffad A
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Of course, in this example we could use &lt;code&gt;rebase&lt;/code&gt; in order to avoid duplicate commits, but one can think of a scenario where the second branch would be a long lived one and would need for only a hotfix to be applied from the upstream.&lt;/p&gt;

&lt;h1&gt;
  
  
  Working with others
&lt;/h1&gt;

&lt;p&gt;So, what do you do in case that you are &lt;strong&gt;not&lt;/strong&gt; the only one that needs these precious fixes? Naturally, the other person will try to search, with the commit message, the desired commit. Guess what, you will find more than one commit and you won’t know which one to apply. One could of course try to change the commit name so it can hint that it’s a &lt;code&gt;cherry-pick&lt;/code&gt; commit and not the original one. This can be done with the following command:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;git cherry-pick &amp;lt;target commit SHA&amp;gt; -e
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This will open an editor where you can change the commit message and append something that hints that this is a &lt;code&gt;cherry-pick&lt;/code&gt; commit.&lt;/p&gt;

&lt;p&gt;After some digging I found that there is another option which automatically appends &lt;em&gt;&lt;code&gt;(cherry picked from commit &amp;lt;original commit's SHA&amp;gt;)&lt;/code&gt;&lt;/em&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;git cherry-pick &amp;lt;target commit SHA&amp;gt; -x
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;At least now you know which commit is cherry-picked or not and what was the original commit as well.&lt;/p&gt;

&lt;p&gt;Cover image by &lt;a href="https://unsplash.com/@rzunikoff?utm_medium=referral&amp;amp;utm_campaign=photographer-credit&amp;amp;utm_content=creditBadge"&gt;Robert Zunikoff&lt;/a&gt; on &lt;a href="https://unsplash.com/s/photos/cherry?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText"&gt;Unsplash&lt;/a&gt;&lt;/p&gt;

</description>
      <category>git</category>
    </item>
    <item>
      <title>Kotlin data vs open class</title>
      <dc:creator>Kostas Tsalikis</dc:creator>
      <pubDate>Thu, 29 Mar 2018 19:45:19 +0000</pubDate>
      <link>https://forem.com/tsalikispk/kotlin-data-vs-open-class-2ckn</link>
      <guid>https://forem.com/tsalikispk/kotlin-data-vs-open-class-2ckn</guid>
      <description>&lt;h2&gt;
  
  
  The Kotlin &lt;em&gt;data&lt;/em&gt; class
&lt;/h2&gt;

&lt;p&gt;One of the many handy features that the Kotlin language offers is the &lt;em&gt;data&lt;/em&gt; keyword. When we declare a class with the &lt;em&gt;data&lt;/em&gt; keyword the compiler implements the &lt;em&gt;equals(Object o)&lt;/em&gt;,&lt;em&gt;hashCode()&lt;/em&gt; and &lt;em&gt;toString()&lt;/em&gt; methods, thus saving us from the trouble to do it manually. The &lt;a href="https://kotlinlang.org/docs/reference/data-classes.html"&gt;official documentation&lt;/a&gt; provides comprehensive examples and nowadays it has become a widely known language feature, so an example can be left outside of the scope of this post.&lt;/p&gt;

&lt;h2&gt;
  
  
  All classes in Kotlin are by default &lt;em&gt;final&lt;/em&gt;
&lt;/h2&gt;

&lt;p&gt;Another thing that Kotlin does behind the scenes is to compile every class that you declare as &lt;em&gt;final&lt;/em&gt;, unless you add the &lt;em&gt;open&lt;/em&gt; keyword to it. We can see how the language is influenced from &lt;em&gt;Effective Java 2nd Edition&lt;/em&gt;(Edition 3 is out as well!). More specifically, items 16 and 17 state the following:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Item 16: Favor composition over inheritance&lt;/p&gt;

&lt;p&gt;Item 17: Design and document for inheritance or else prohibit it&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h2&gt;
  
  
  A clash between keyword definitions
&lt;/h2&gt;

&lt;p&gt;This is a very nice feature of the language, as it tries to protect us from the various perils of improper use of inheritance, as it is described in the book. Unfortunately, things begin to become messy when you try to declare a class both open and data. The compiler will complain that a data class cannot be at the same time open, giving us an error.&lt;/p&gt;

&lt;p&gt;Let’s stop for a moment and consider why the architects of the language decided to impose such an obstacle. First of all, we will try to remember some wise words from the &lt;em&gt;Growing object-oriented systems, driven by tests&lt;/em&gt; book from Steve Freeman and Nat Pryce. Chapter 2 presents a distinction between &lt;em&gt;values&lt;/em&gt; and &lt;em&gt;objects&lt;/em&gt;. &lt;em&gt;Objects&lt;/em&gt; communicate between each other by sending messages and have some specific behavior depending on their state. If their state changes, so does their behavior. On the other hand &lt;em&gt;values&lt;/em&gt; - to paraphrase - are just bags of data, used for computations.&lt;/p&gt;

&lt;p&gt;Now that the definition and distinction between &lt;em&gt;objects&lt;/em&gt; and &lt;em&gt;values&lt;/em&gt; is clear, we can see that it does makes sense for Kotlin to impose such rules when using the &lt;em&gt;data&lt;/em&gt; and &lt;em&gt;open&lt;/em&gt; keywords. A &lt;em&gt;data&lt;/em&gt; class is a &lt;em&gt;value&lt;/em&gt;, holding only - preferably immutable - data without behavior. Since it makes sense to extend a class in order to change its behavior and the &lt;em&gt;data&lt;/em&gt; class has no behavior, why should we be able to extend it?&lt;/p&gt;

&lt;p&gt;Although the reasons for this design decision are quite valid, the imposed restrictions make the transition from Java to Koltin difficult. We may have in our codebase a class that’s a perfect candidate to become a data class, but if for some reason this class is extended by another class, you cannot make that transition instantly, as you have to fix first the fact that the class is extended. The problem becomes even worse when we have a deep nested hierarchy.&lt;/p&gt;

&lt;h2&gt;
  
  
  Some scenarios and possible ways to tackle the problem
&lt;/h2&gt;

&lt;p&gt;One way to deal with this, is to check if the class has any fields or not. If it doesn’t have and it just acts as a marker, we could go and delete that class, trace the compiler errors and replace with the parent class. Indeed we can use this technique, provided that child class is not used in any &lt;em&gt;instanceOf&lt;/em&gt; checks. In that case the problem becomes even worse especially when the parent class is involved in the &lt;em&gt;instanceOf&lt;/em&gt; checks as well. Here we have a behavioural change in the system which we cannot fix just by replacing the check with the parent class, one that is very difficult to change. The sins of the past have finally caught up with us.&lt;/p&gt;

&lt;p&gt;Now let’s consider the case where the child class extends the parent just to inherit some or all the fields of the parent and adds its own as well. Then we could try to use some kind of composition depending on the case.&lt;/p&gt;

&lt;h2&gt;
  
  
  Final thoughts
&lt;/h2&gt;

&lt;p&gt;Maybe the nastiest of the problems described above is the &lt;em&gt;instanceOf&lt;/em&gt; checks. If we could find a way to get past these checks problem, then replacing the children with the parent or passing the parent as a dependency becomes less difficult.&lt;/p&gt;

&lt;p&gt;Unfortunately, this post does not provide a final solution, but rather tries to reason with Kotlin’s implementation decisions and explore some thoughts on how to tackle the problems that arise during a Java to Kotlin migration.&lt;/p&gt;

</description>
      <category>kotlin</category>
    </item>
    <item>
      <title>Architecture Decision Records</title>
      <dc:creator>Kostas Tsalikis</dc:creator>
      <pubDate>Wed, 14 Feb 2018 12:42:41 +0000</pubDate>
      <link>https://forem.com/tsalikispk/architecture-decision-records-14b1</link>
      <guid>https://forem.com/tsalikispk/architecture-decision-records-14b1</guid>
      <description>&lt;p&gt;In a &lt;a href="https://www.droidship.com/posts/branch-by-abstraction/"&gt;previous post&lt;/a&gt;, we tackled the problem of doing a large change in your system incrementally. During refactoring, you can stumble upon a lot of problems, but one of the greatest is, how do you react to a past decision that you cannot understand? Do you accept it, with the risk of continuing to pay the technical debt associated with it? Or do you discard it, with the risk of losing some important semantics that should’t be lost along the way?&lt;/p&gt;

&lt;p&gt;If you’re lucky enough, the person that made that decision will be one or two desks away. On the other hand, there is a high probability that the decision above was made a long time ago, and that person is long gone from the company you’re working. The only way to keep technical decisions without being lost is to document them. But where and how do you do it?&lt;/p&gt;

&lt;p&gt;Most often, saving the decisions in some kind of wiki is not going to work. Large documentation files are scarcely updated along with the code, and most developers just lose their focus when they have to move away from the code and filter a large document. What’s more, you can’t keep that kind of files in version control due to their size.&lt;/p&gt;

&lt;h2&gt;
  
  
  Documenting with Architecture Decision Records.
&lt;/h2&gt;

&lt;p&gt;The key in having successful documentation is to keep it updated in version control in small files. This is what Michael Nygard proposed in his &lt;a href="http://thinkrelevance.com/blog/2011/11/15/documenting-architecture-decisions"&gt;Architecture Decision Records&lt;/a&gt;(from now on &lt;em&gt;ADRs&lt;/em&gt;). ADRs are text files that save the architecture decisions taken over time and have the following format:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Title:&lt;/strong&gt; A small descriptive title of the decision.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Context:&lt;/strong&gt; A description of the constraints under whom the decision was made.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Decision:&lt;/strong&gt; The actual decision.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Status:&lt;/strong&gt; Whether or not the decision is proposed/accepted, or amended/superseded by another decision.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Consequences:&lt;/strong&gt; The consequences that this decision will have.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Keeping ADRs is a powerful technique, as it captures not only the decisions, but under what circumstances were made and documents the consequences at the time that the decision was actually made.&lt;/p&gt;

&lt;p&gt;Even when a decision is superseded or amended by another one, Michael Nygard suggests that you never delete it, but mark it as superseded by the new decision. This way you can see how the code has evolved over time and you can also checkout from version control the commit that the decision was made and see what forces drove the author of the decision to make it.&lt;/p&gt;

&lt;p&gt;Before presenting the appropriate tooling to successfully keep documentation of our decisions, let’s question ourselves, what kind of decisions should we document? If we end up saving every little detail, then the objective of keeping the documentation as small as possible and to the point fails. As Michael Nygard puts it himself, the decisions that we ought to keep are:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;those that affect the structure, non-functional characteristics, dependencies, interfaces, or construction techniques&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h2&gt;
  
  
  Tools for using ADRs
&lt;/h2&gt;

&lt;p&gt;So let’s say that you’re now convinced that saving ADRs is a technique worth giving a shot. How should you implement it? Fortunately, Nat Pryce has made available his &lt;a href="https://github.com/npryce/adr-tools"&gt;ADR Tools&lt;/a&gt;. ADR Tools is a set of command lines that create ADRs in markdown. The installation instructions are available &lt;a href="https://github.com/npryce/adr-tools/blob/master/INSTALL.md"&gt;here&lt;/a&gt;. After installing, you just have to type the following command:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;adr init your/documentation/directory
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This will create the very first ADR, saved in a markdown file. It’s also worth noting that the first thing documented is your decision to start using ADRs.&lt;/p&gt;

&lt;p&gt;When you will add a new ADR you will simply give the following command:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;adr new Name of the decision
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;A more exhaustive description of how to use ADR Tools is available &lt;a href="https://github.com/npryce/adr-tools"&gt;here&lt;/a&gt; or you can use the command line:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;adr help
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Except from the help command above, Nat Pryce has also written down the decisions that were made during the development of the Tools as &lt;a href="https://github.com/npryce/adr-tools/tree/master/doc/adr"&gt;ADRs&lt;/a&gt;. This is a helpful example of real life usage of ADRs, that can guide us during our(let’s be honest with ourselves, not so fascinating) journey to meaningful documentation.&lt;/p&gt;

&lt;h2&gt;
  
  
  Final thoughts
&lt;/h2&gt;

&lt;p&gt;Keeping ADRs seems to be a good way to save decisions that will later give good insight during refactoring. It is quite possible that you will not be the person responsible for that refactoring, or even if you are, then Eagleson’s law will be applied:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Eagleson's Law: Any code of your own that you haven't looked at for six or more months might as well have been written by someone else.&lt;/p&gt;

&lt;p&gt;— Programming Wisdom (&lt;a class="mentioned-user" href="https://dev.to/codewisdom"&gt;@codewisdom&lt;/a&gt;
) &lt;a href="https://twitter.com/CodeWisdom/status/940007477642432514?ref_src=twsrc%5Etfw"&gt;December 10, 2017&lt;/a&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Before starting coding a decision that affects the architecture of a system, I think maybe it should be better to write it down as an ADR(just as you would first add a test before the real implementation in TDD).&lt;/p&gt;

&lt;p&gt;This way, you are obliged to document the constraints under which you made the decision as the &lt;em&gt;Context&lt;/em&gt; of the ADR, and document the &lt;em&gt;Consequences&lt;/em&gt; as well, so you are in a position to validate that the change that you are about to introduce is built upon sound foundations.&lt;/p&gt;

&lt;p&gt;What’s more, even if you change your mind about that decision and want to amend it with another one, you will already have documented it. The next person that will see the documentation, will be available to see a train of thoughts, and not a ladder that has some steps skipped. The decisions will make more sense, and that person will be in a position to better understand them, and in return accept or modify them.&lt;/p&gt;

</description>
      <category>documentation</category>
    </item>
    <item>
      <title>Branch by Abstraction powered by Kotlin</title>
      <dc:creator>Kostas Tsalikis</dc:creator>
      <pubDate>Sun, 21 Jan 2018 18:34:20 +0000</pubDate>
      <link>https://forem.com/tsalikispk/branch-by-abstraction-powered-by-kotlin-2i6k</link>
      <guid>https://forem.com/tsalikispk/branch-by-abstraction-powered-by-kotlin-2i6k</guid>
      <description>&lt;h2&gt;
  
  
  A case of a large-scale refactoring.
&lt;/h2&gt;

&lt;p&gt;Let’s say that one day your senior comes and tells you, “Hi Christine, I’ve checked out this new cool library X that solves problem Y, can you try to change some calls as a proof of concept and in the meantime provide us with your feedback on how it affects us?”&lt;/p&gt;

&lt;p&gt;So you become excited, you get the opportunity to dirt your hands with this new hotness that everyone in the community speaks about, and prove yourself to the team. AWESOME!&lt;/p&gt;

&lt;p&gt;As you go about the documentation, you get the feeling that this library is really a lifesaver, and should indeed be integrated with the rest of the codebase. On the downside, there is big gotcha. Migrating from the current implementation to the new is not going to be easy. Your only choice is to create a new branch with the new feature, and merge it back to the trunk(a.k.a. master). Or is it not? You don’t want to be the one to make that huge pull request. You only need to implement that small set of simple calls to the new library and leave the rest be. How do you do it?&lt;/p&gt;

&lt;h2&gt;
  
  
  Enter Branch by Abstraction.
&lt;/h2&gt;

&lt;p&gt;Bearing in mind that you do not want to be in a situation of a huge merge, and that the changes need to be published to the rest of the team as soon as possible, with some research you can stumble upon a technique named &lt;em&gt;“Branch by abstraction”&lt;/em&gt;(BbA for the rest of the post). Originally it was introduced by &lt;a href="https://paulhammant.com/2013/04/05/what-is-trunk-based-development/" rel="noopener noreferrer"&gt;Paul Hammant&lt;/a&gt; and described by &lt;a href="https://continuousdelivery.com/2011/05/make-large-scale-changes-incrementally-with-branch-by-abstraction/" rel="noopener noreferrer"&gt;Jez Humble&lt;/a&gt; as well.&lt;/p&gt;

&lt;p&gt;But what exactly is BbA and how does it differ from the classic feature branching in version control?&lt;/p&gt;

&lt;p&gt;Quoted directly from &lt;a href="https://martinfowler.com/bliki/BranchByAbstraction.html" rel="noopener noreferrer"&gt;Martin Fowler&lt;/a&gt;:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;“Branch by Abstraction” is a technique for making a large-scale change to a software system in gradual way that allows you to release the system regularly while the change is still in-progress.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;The name of the technique is a little bit misleading, as it contains the term “branch” in its definition, which almost immediately hints that we’re speaking about branching as in creating a new branch in source control. On the contrary, the technique is advocated by &lt;a href="https://trunkbaseddevelopment.com/" rel="noopener noreferrer"&gt;trunk based development&lt;/a&gt;, a source control branching model where all developers push directly in the mainline. Rather than branching in source control, the &lt;em&gt;“branching”&lt;/em&gt; happens in the code directly.&lt;/p&gt;

&lt;p&gt;Let’s say the initial structure of your code is something like this:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fwww.droidship.com%2Fimages%2Fposts%2Fbba%2Finitial_structure.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fwww.droidship.com%2Fimages%2Fposts%2Fbba%2Finitial_structure.png" alt="Initial structure"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Initial Structure.&lt;/p&gt;

&lt;p&gt;The steps for BbA are:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Add an abstraction over the current old implementation.&lt;/li&gt;
&lt;li&gt;Refactor so all the clients use the abstraction above instead of the old implementation directly.
&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fwww.droidship.com%2Fimages%2Fposts%2Fbba%2Fstep1-2.png" alt="Steps 1 &amp;amp; 2"&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Steps 1 &amp;amp; 2.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Add the new implementation under that abstraction and gradually delegate to the new implementation as needed.
&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fwww.droidship.com%2Fimages%2Fposts%2Fbba%2Fstep3.png" alt="Step 3"&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Step 3.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Once the old implementation is no longer used, it can be deleted.
&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fwww.droidship.com%2Fimages%2Fposts%2Fbba%2Fstep4.png" alt="Step 4"&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Step 4.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Once the refactoring is over, delete the abstraction layer.
&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fwww.droidship.com%2Fimages%2Fposts%2Fbba%2Fstep5.png" alt="Step 5"&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Step 5.&lt;/p&gt;

&lt;p&gt;Although Martin Fowler describes some variations, the general idea is that you create an abstraction over the implementation that needs replacement, find the appropriate behaviour that the abstraction must implement, change the client code to use that abstraction and incrementally add the new code.&lt;/p&gt;

&lt;p&gt;What’s more you can use &lt;a href="https://martinfowler.com/articles/feature-toggles.html" rel="noopener noreferrer"&gt;feature toggles&lt;/a&gt;, so you continue to deliver software, even if the the new implementation is unfinished.&lt;/p&gt;

&lt;h2&gt;
  
  
  Pros and Cons
&lt;/h2&gt;

&lt;p&gt;Every technique has its ups and downs, and BbA is no short of its own:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Pros&lt;/strong&gt; :&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;No merge hell.&lt;/li&gt;
&lt;li&gt;It is possible to extract behaviour that the old implementation should’t have, thus making the system more cohesive.&lt;/li&gt;
&lt;li&gt;Code is continuously integrated, thus always on a working state.&lt;/li&gt;
&lt;li&gt;You can deliver anytime, even with the feature unfinished.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Cons&lt;/strong&gt; :&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Development process may slow down, as it is not always easy to introduce the required abstraction, or to make the two implementations co-exist during the refactoring.&lt;/li&gt;
&lt;li&gt;Difficult to apply if the code needs external audit.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Show me the code
&lt;/h2&gt;

&lt;p&gt;Of course, talk is cheap and a simple but non trivial example is worth a thousand words. Let’s create a simple app which saves quotes and then lists them(named with an extra dose of imagination “QuotesApp”).&lt;/p&gt;

&lt;p&gt;For QuotesApp we will use a MVP pattern. The Presenters will hold a QuotesRepository directly instead of UseCases and the QuotesRepository will have a QuotesDataSource for storing the quotes locally. In the role of our legacy library we will use SqlBrite2 and we will try to replace it gradually with the new Room library. The full code of the example is &lt;a href="https://github.com/tsalik/BranchByAbstractionExample" rel="noopener noreferrer"&gt;here&lt;/a&gt;.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;public interface QuotesDataSource {

    Observable&amp;lt;List&amp;lt;Quote&amp;gt;&amp;gt; getSavedQuotes();

    Observable&amp;lt;Boolean&amp;gt; add(Quote quote);

}

public class SqlBriteQuotesDataSource implements QuotesDataSource {

    private final BriteDatabase briteDatabase;

    public SqlBriteQuotesDataSource(BriteDatabase briteDatabase) {
        this.briteDatabase = briteDatabase;
    }

    @Override
    public Observable&amp;lt;List&amp;lt;Quote&amp;gt;&amp;gt; getSavedQuotes() {
        // get quotes with SqlBrite
    }

    @Override
    public Observable&amp;lt;Boolean&amp;gt; add(Quote quote) {
        // save a quote with SqlBrite
    }
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We will use the QuotesDataSource interface to introduce the abstraction needed for our BbA powered refactoring. In Java this would look something like below. We would make the abstraction implement the QuotesDataSource and then manually delegate all method calls to the old implementation. Then in our dependency injector we would wrap the Sqlite implementation with the new mixed data source.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;public class MixedSqliBriteRoomDataSource implements QuotesDataSource {

    private final QuotesDataSource oldDataSource;

    public MixedSqliBriteRoomDataSource(QuotesDataSource oldDataSource) {
        this.oldDataSource = oldDataSource;
    }

    @Override
    public Observable&amp;lt;List&amp;lt;Quote&amp;gt;&amp;gt; getSavedQuotes() {
        return oldDataSource.getSavedQuotes();
    }

    @Override
    public Observable&amp;lt;Boolean&amp;gt; add(Quote quote) {
        return oldDataSource.add(quote);
    }

}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Excuse me, where is my Kotlin twist?
&lt;/h2&gt;

&lt;p&gt;In this example we only have two methods, but one can imagine a huge api with a hundred or more methods. Wouldn’t it be tedious and error prone to manually delegate to the old implementation? So far, Kotlin has not shown up in the post, and now is the time to make its magical appearance. We could use the power of Kotlin’s built in delegation and make the abstraction delegate by default to the old implementation:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;class MixedSqliteRoomDataSource(private val oldDataSource: QuotesDataSource)
: QuotesDataSource by oldDataSource
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is not only terse and concise, but also saves you from the errors that anyone can easily do during manual delegation.&lt;/p&gt;

&lt;h2&gt;
  
  
  Back to Refactoring
&lt;/h2&gt;

&lt;p&gt;Continuing with the refactoring, we would introduce the new implementation, and pass it as a second argument to our abstraction. Then finally, we would override only some of the methods in our abstraction to delegate to the new implementation.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;class MixedSqliteRoomDataSource(private val oldDataSource: QuotesDataSource,
                                private val newDataSource: QuotesDataSource)
    : QuotesDataSource by oldDataSource {

    override fun getSavedQuotes(): Observable&amp;lt;MutableList&amp;lt;Quote&amp;gt;&amp;gt; {
        return newDataSource.savedQuotes
    }

}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is much easier to push directly to the mainline, or if you’re in favour of code reviews, make a short lived version control branch and open a pull request from there.&lt;/p&gt;

&lt;p&gt;As you add more and more methods in your new implementation, the old one and the abstraction will become obsolete, and finally you will be able to delete them.&lt;/p&gt;

&lt;h2&gt;
  
  
  Final Thoughts
&lt;/h2&gt;

&lt;p&gt;So far, BbA seems to be quite a sane way for making large-scale changes in your codebase. It may not be always easy to make the old and new implementations coexist, but all in all, it seems to be worth the effort. What’s more, we can use the power of Kotlin’s delegation to quickly implement only a set of behaviours in order to provide a proof of concept, and then continue with the rest of the refactoring.&lt;/p&gt;

</description>
      <category>kotlin</category>
      <category>refactoring</category>
      <category>cicd</category>
    </item>
    <item>
      <title>Blogging with Hugo and Netlify</title>
      <dc:creator>Kostas Tsalikis</dc:creator>
      <pubDate>Sat, 13 Jan 2018 22:34:25 +0000</pubDate>
      <link>https://forem.com/tsalikispk/blogging-with-hugo-and-netlify-541p</link>
      <guid>https://forem.com/tsalikispk/blogging-with-hugo-and-netlify-541p</guid>
      <description>&lt;p&gt;Hi everyone, and welcome to my first ever blogpost! I’ve been meaning to begin a technical blog about Android development for ages, and at last the time has come. This first post, however, will not be Android related – instead I will break down why and how I chose Hugo and deployed this site.&lt;/p&gt;

&lt;h2&gt;
  
  
  Hugo vs Jekyll
&lt;/h2&gt;

&lt;p&gt;As I needed something easy to setup and customize, a static site made perfect sense – and there are lots of &lt;a href="https://www.staticgen.com/"&gt;static site generators&lt;/a&gt; to choose from. In fact there are too many, so I decided to play with the two highest ranked, &lt;a href="https://jekyllrb.com/"&gt;Jekyll&lt;/a&gt; (Ruby) and &lt;a href="http://gohugo.io/"&gt;Hugo&lt;/a&gt; (Go), which both have strong communities and offer a plethora of themes.&lt;/p&gt;

&lt;p&gt;Both are fun, but with Jekyll you have to deal with Ruby and RubyGems. On the other hand, the only thing that Hugo needs is the Go executable. In the end I chose Hugo, as I wouldn’t have to live with the pain of dealing with Ruby again in case of migrating to another environment, and overall I felt that Hugo worked pretty straightforward for me. Installing and tweaking Hugo is pretty easy if you follow the &lt;a href="http://gohugo.io/getting-started/"&gt;documentation&lt;/a&gt;, so I’ve left it outside of the scope of this post.&lt;/p&gt;

&lt;h2&gt;
  
  
  Hosting on Netlify
&lt;/h2&gt;

&lt;p&gt;As an Android developer, I cannot say that I had prior experience on how to deploy a site. What I can say, however, is that this was one of the biggest hurdles that I faced in the process of setting up this blog. Fortunately, Hugo has a lot of &lt;a href="https://gohugo.io/hosting-and-deployment/"&gt;suggestions on hosting and deployment&lt;/a&gt; which saved the day. Among the proposals, that of &lt;a href="https://www.netlify.com/"&gt;Netlify&lt;/a&gt; seemed to be the most attractive, with the promise of Continuous Deployment, custom domain name and 1-click HTTPS.&lt;/p&gt;

&lt;p&gt;Of course, there was no way that the whole setup would go as planned right away. Firstly, I wasn’t even able to deploy the site. Being quite forgetful myself, I had missed to add the wonderful Hugo theme that I had chosen as a git submodule. After that, the site was up, but something in the theming had gone awfully wrong. Once again, I had forgotten to change the baseURL in the &lt;em&gt;config.toml&lt;/em&gt;, which contains configuration for the Hugo site.&lt;/p&gt;

&lt;p&gt;And then, oh joy! The site was live – but not exactly as I had managed to do locally in my machine. Since everything was a draft, the blog was just empty. The trick was to add a &lt;em&gt;netlify.toml&lt;/em&gt; file, which configures the Netlify deployment, and edit it to run a different command that builds drafts in Hugo. Then with a pull request in Github, a new preview environment was created in Netlify, and I could verify that the blog was up as intended with the drafts built. This is extremely useful, because we can share drafts with reviewers or make UI changes without affecting the production site.&lt;/p&gt;

&lt;h2&gt;
  
  
  Ready, aim, fire!
&lt;/h2&gt;

&lt;p&gt;Finally, with the site live, I’m ready to start my journey in technical blogging. I wish to be a frequent writer and share my ideas (mostly) about Android development with the rest of the community. Hopefully, this blog will be a platform where knowledge will be shared among us, both for me and for you – the readers – in an environment of mutual respect and understanding.&lt;/p&gt;

</description>
      <category>hugo</category>
      <category>blogging</category>
    </item>
  </channel>
</rss>
