You are on page 1of 47

Kotlin’s Coroutine 101

How to achieve scalable Asynchronous Programming

By : Javentira Lienata (Android Developer at Bukalapak)

1
HELLO!
I am Javentira Lienata one of Bukalapak’s Android Devs
I am here because sharing is caring.

2
Career History

● AnalisaDaily.com Web Developer ( 2015 - 2016 )

● AjoMedan.com (Daily Deals) Managing Director ( 2015 - 2016 )

● Paprika MultiMedia Web Developer ( 2016 )

● Paprika MultiMedia Mobile Apps Developer Java and React Native ( 2016 - 2017 )

● Bukalapak Mobile Apps Developer ( 2017 - Present )

3
Agenda

● Introduction
○ What is Coroutine?
○ Why Coroutine?

● Basic and Practices


○ Suspend Functions
○ Coroutine Builder
○ Job
○ Coroutine Dispatcher
○ Structured Concurrency
○ Coroutine Scope

4
Introduction
What is Coroutine?

5
What is Coroutine?

● The Kotlin team defines coroutines as “lightweight threads”

● Coroutine is similar to thread

6
Coroutine Vs Thread

Similarity :

- Both are sequence of instructions


- Multiple Coroutines or Threads can be executed concurrently
- Multiple Coroutines or Threads share resources such as memory

Difference :

- Coroutine = lightweight Thread


- Coroutines run in a Thread

7
Coroutine Vs Thread

Similarity :

- Both are sequence of instructions


- Multiple Coroutines or Threads can be executed concurrently
- Multiple Coroutines or Threads share resources such as memory

Difference :

- Coroutine = lightweight Thread


- Coroutines run in a Thread
Thread

Coroutines

8
What is Coroutine?

● The Kotlin team defines coroutines as “lightweight threads”

● Coroutine is similar to thread

● Thread-independent and Suspendable subroutine(subprogram) which can call


each-other

● An approach to Asynchronous Programming

9
Introduction
Why Coroutine?

10
Why Coroutine?

● Long Blocking task should be executed asynchronously

● Possible solutions:
- Threading
- Callbacks
- Futures / Promises
- Reactive Extensions

11
Why Coroutine?

● Long Blocking task should be executed asynchronously

● Possible solutions:
- Threading ( expensive )
- Callbacks
- Futures / Promises
- Reactive Extensions

12
Why Coroutine?

● Long Blocking task should be executed asynchronously

● Possible solutions:
- Threading ( expensive )
- Callbacks ( difficult to understand, callback hell, can’t handle exception )
- Futures / Promises
- Reactive Extensions

13
Why Coroutine?

14
Why Coroutine?

● Long Blocking task should be executed asynchronously

● Possible solutions:
- Threading ( expensive )
- Callbacks ( difficult to understand, callback hell, can’t handle exception )
- Futures / Promises
- Reactive Extensions

15
Why Coroutine?

● Long Blocking task should be executed asynchronously

● Possible solutions:
- Threading ( expensive )
- Callbacks ( difficult to understand, callback hell, can’t handle exception )
- Futures / Promises ( easier than callback, but still can’t handle leak? )
- Reactive Extensions

16
Why Coroutine?

● Long Blocking task should be executed asynchronously

● Possible solutions:
- Threading ( expensive )
- Callbacks ( difficult to understand, callback hell, can’t handle exception )
- Futures / Promises ( easier than callback, but still can’t handle leak? )
- Reactive Extensions ( steep learning curve, coroutines are easier to understand )

17
Basic and Practices
Suspend Function?

18
Suspend Functions

● Marked with suspend modifier

● Suspend the execution of the code without blocking the current thread of execution

19
Suspend Functions

● Marked with suspend modifier

● Suspend the execution of the code without blocking the current thread of execution

20
Suspend Functions

21
Basic and Practices
Coroutine Builder

22
Coroutine Builder

1 2
launch async

● Fire and forget ● Fire and gives result


● Doesn’t have any result ● Returns Deferred
● Returns Job

3
runBlocking
● Blocks current thread

23
Coroutine Builder

launch

async

24
Coroutine Builder

runBlocking

25
Basic and Practices
Job & Deferred

26
Job

Job Deferred

● Cancelable thing ● Implement Job


● Has a life-cycle ● Light-weight non-blocking
● Destroys when its future
complete ● await()to wait the result

27
Basic and Practices
Coroutine Dispatcher

28
Coroutine Dispatcher

● Determines what thread or threads the corresponding coroutine uses for its execution.
○ Confine (restrict) coroutine execution to a specific thread
○ Dispatch it to a thread pool
○ Or let it run unconfined (unrestricted)

29
Coroutine Dispatcher

1 2
Dispatcher.Default Dispatcher.IO
● Used by default in all standard builder ● Uses a shared pool of on-demand
● Uses common pools of shared bg created threads
thread ● Used for IO tasks

3 4
Dispatcher.Unconfined Dispatcher.Main
● Unrestricted to any specific thread or ● Confined to the Main thread operating
pool with UI objects
● Shouldn’t be used normally in code ● Should add corresponding artifact

30
Coroutine Dispatcher

5 6
newSingleThreadContext newFixedThreadPoolContext
● To create new private single-threaded ● To create private thread pool of fixed
coroutine context. size.

7
asCoroutineDispatcher
● Extension function to convert Executor
to dispatcher.

31
Coroutine Dispatcher

Notes :

● Launch and async accept optional dispatcher


● Launch(Dispatchers.Default) { … } uses the same dispatcher as
GlobalScope.launch { … }

32
Coroutine Dispatcher

33
Coroutine Dispatcher

34
Coroutine Dispatcher

The second println operation prints kotlinx.coroutines.DefaultExecutor because delay suspends the coroutine using the
default scheduler.

35
Basic and Practices
Structured Concurrencies

36
Structured Concurrencies

● Coroutines are light weight, How about run all business logic/code using
GlobalScope.launch?

● New Problem:
○ It still consumes some memory resources while it runs.
○ Leak!!
○ What if the code in the coroutine hangs?

37
Structured Concurrencies

Solution 1
Store the job, and cancel it on certain lifecycle

38
Structured Concurrencies

Solution 1
Store the job, and cancel it on certain lifecycle

Well… Don’t you think it’s too complicated?


39
Structured Concurrencies

Well that’s where Structured Concurrencies in Coroutines comes in handy. How?

By Using….

40
Basic and Practices
Coroutine Scope

41
Coroutine Scope

Solution 2
Use Coroutine Scope in some local Scope like UI Element with well defined lifecycle

42
Coroutine Scope

● We can define scope for each coroutine

● Every coroutine builder is an extension on CoroutineScope

● CoroutineScope provides properties like coroutineContext and it is a set of various


elements like Job of the coroutine and its dispatcher

● GlobalScope -> CoroutineScope with a lifetime of the whole application.

43
Jadi apa saja manfaat Coroutines?

44
Jadi apa saja manfaat Coroutines?

● Concurrency tanpa callback hell dan branching paths

● Suspend Function akan selalu aman dipanggil, biarpun dari main thread

● Dispatcher bisa memproses ribuan job, no problem.

● Coroutine Scope menjaga tidak ada job yg leak

● Better Concurrency -> faster & efficient app

45
Resources Link

- https://proandroiddev.com/how-to-make-sense-of-kotlin-coroutines-b666c7151b93
- https://www.youtube.com/watch?v=EOjq4OIWKqM
- https://www.youtube.com/watch?v=BXwuYykIxbk
- https://www.youtube.com/watch?v=jT2gHPQ4Z1Q
- credits to Wahid Nur Rohman ( Android Developer at Bukalapak )
- credits to Andika Pratama ( Android Developer at Bukalapak )

46
THANKS!
and
Have A Great Kotlin!

47

You might also like