Droidcon Boston 2018 Conference Report
Attendees and speakers descended upon Boston this week for Droidcon Boston 2018. Learn what you missed and what to watch to hone your Android app development skills. By Joe Howard.
Sign up/Sign in
With a free Kodeco account you can download source code, track your progress, bookmark, personalise your learner profile and more!
Create accountAlready a member of Kodeco? Sign in
Sign up/Sign in
With a free Kodeco account you can download source code, track your progress, bookmark, personalise your learner profile and more!
Create accountAlready a member of Kodeco? Sign in
Contents
Droidcon Boston 2018 Conference Report
45 mins
- Day 1
- Community Addiction: The 2nd Edition
- Keynote: Tips for Library Development from a Startup Developer
- Pragmatic Gradle for Your Multi-Module Projects
- Lunch & a Lightning Talk: Background Processing
- Practical Kotlin with a Disco Ball
- TensorFlow for Android Developers
- Workshop: Hands on Android Things
- Day 2
- Keynote: Design + Develop + Test
- fun() Talk
- Common Poor Coding Patterns and How to Avoid Them
- Lunch & a Lightning Talk: Reactive Architecture
- ARCore for Android Developers
- Why MVI? Model View Intent — The curious case of yet another pattern
- Coroutines and RxJava: An asynchronicity comparison
- Where to go from here?
Why MVI? Model View Intent — The curious case of yet another pattern
Garima Jain, Senior Android Engineer, Fueled
Garima gave a great talk on the Model-View-Intent (MVI) pattern. There were two parts to the talk: (1) Why MVI and (2) moving from MVP/MVVM to MVI.
First, why MVI? She defined MVI as a mapping from (Model, View, Intent) to (State, View, Intention). And add a user into the picture and MVI becomes different from other patterns. The user interacts with the View, the intent changes state, goes to the view, and is seen by user.
The key concept is State as a single source of truth. A common example of the State problem is: what is going on with state when doing a pull to refresh – the state of a list. The state problem is a main reason people are motivated to follow MVI. First there’s a loading state, then an empty state, then pull to refresh but with the empty state still showing. The View is not updating state correctly.
Garima used an MVP diagram to represent the problem. If you misuse MVP, some of the state is in the view and some is in the presenter. Multiple inputs and outputs cause the possibility of misuses. The MVI pattern helps here. MVI has single source of state truth. This is sometimes called the Hannes model, after Hannes Dorfmann.
Part 2 of the talk discussed moving from MVP/MVVM to MVI. How to move to MVI if you have other patterns already in place. You don’t have to go all the way to MVI right away. Call it “MVPI”. Build on top of MVP or MVVM.
Garima gave a great description of data flow in the MVI pattern. From a UI event in the View, the event gets transformed to an Action sent to the Presenter, then sent to a Reducer as a Result. The reducer creates new state which gets rendered to the View. She discussed applying the pattern to the loading problem. State is an immutable object. You create a new one to show in the view after a user interaction. Now there is only one state, one source of truth for the model. Changes only occur due to actions.
She gave some good rules of thumb. Action should be a plain object that has a type that is not undefined and conveys the intention of the user. State is an immutable list or object representing the state of the view. The Reducer is a function of the previous state and the result. It returns the current state for an unknown result. Use a Kotlin sealed class for the different kinds of results.
In summary, Garima mentioned that many consider that MVI is MVP/MVVM done right. It prevents us from misusing patterns like MVP and MVVM. She also gave some great refrerences:
Coroutines and RxJava: An asynchronicity comparison
Manuel Vicente Vivo, Principal Associate Software Engineer, Capital One
Manual is comparing coroutines and RxJava because they’re both trying to solve the same problem: asynchronous programming.
He started with a coroutines recap, compared the libraries, and demoed a Fibonacci calculator with fun facts from an API.
Coroutines simplify asynchronous programming. Computations can be suspended without blocking a thread. They’re conceptually similar to a thread. They start and finish and but are not bound to a particular thread.
The launch
function is a coroutine builder. The first parameter is a coroutine context. It takes a suspending lambda as second parameter. For example, making a network request and updating a database with data. The user taps a button and starts a heavy computation. You suspend while waiting for a response from the network. You carry on with execution when the response comes back.
Manuel then gave a detailed coroutine and RxJava comparison.
He showed how to cancel execution in both. In RxJava, call disposable.dispose(). For coroutines, use the coroutine job which is returned from launch and call job.cancel(). You can concatenate coroutine contexts and can cancel them all at the same time. You can also use a parent named argument and cancel the parent.
Manuel defined Channels as the coroutine equivalent of an RxJava Observable and Reactive Streams Publisher. Channels can be shared between different coroutines, with a default capacity of 1. In RxJava, you get values when onNext is called. You use send
and receive
to send/receive elements through the channel, and they are suspending functions. You can close channels. And you can also offer
elements. produce
is another coroutine builder for a coroutine with a Channel built-in. It’s useful to create custom operators.
Channels have to deal with race conditions: which coroutine gets the values first? In RxJava, you use Subjects to handle this issue. BroadcastChannel can be used to send the same value to all coroutines. ConflatedBroadcastChannel behaves similar to an RxJava subject.
What about RxJava back-pressure? It’s handled by default in coroutines, since send and receive are suspending functions.
You can use publish
for a “cold observable” behavior, but it’s in the interop library, a bridge between coroutines and RxJava. Another use case would be calling coroutines from Java.
An Actor is a coroutine with a channel built-in, but the opposite of produce
. Think of it as a mailbox that will process and receive different events.
For the equivalent of RxJava operators, some are built-in to the language in Kotlin collections. Some others are easy to implement. And some are more work, such as zip
.
For threading in RxJava, you use observeOn and subscribeOn. Threading in coroutines is done within the coroutine context. CommonPool, UI (Android), and Unconfined are examples of contexts. You can create your own contexts using ThreadPoolDispatcher.
Manuel finished up with his example application, a math app built with the MVI Architecture. He has three projects: one using coroutines, one using RxJava, and one with interop between the two.
The project uses the Android Architecture Component ViewModel to survive configuration changes, and can be found on GitHub.
Where to go from here?
You can find more info about the Droidcon series of conferences at the official site.
The full agenda for Droidcon Boston 2018, including sessions not covered in this report, can be found here.
The videos from the most recent Droidcon NYC can be found here.
The videos and slides from Droidcon Boston 2017 are here.
We’ll add a link to the videos from Droidcon Boston 2018 when they’re available.
Feel free to share your feedback, findings or ask any questions in the comments below or in the forums. I hope you enjoyed this summary of Droidcon Boston 2018! :]