asynchronous data streams with kotlin flow roman elizarov
play

ASYNCHRONOUS DATA STREAMS WITH KOTLIN FLOW ROMAN ELIZAROV - PowerPoint PPT Presentation

ASYNCHRONOUS DATA STREAMS WITH KOTLIN FLOW ROMAN ELIZAROV @relizarov Copenhagen Copenhagen Denmark Denmark RECAP ON KOTLIN COROUTINES Kotlin Coroutines FTW Callback hell before fun requestTokenAsync(): Promise<Token> { } fun


  1. fun CoroutineScope.foo(): ReceiveChannel<Response> = produce { send( compute ( "A" )) send( compute ( "B" )) send( compute ( "C" )) } A B C foo() Channel<R> send send send A B C main() fun main() = runBlocking { val channel = foo () for (x in channel) println (x) }

  2. fun CoroutineScope.foo(): ReceiveChannel<Response> = produce { send( compute ( "A" )) send( compute ( "B" )) send( compute ( "C" )) } A B C foo() Channel<R> send send send A B C main() fun main() = runBlocking { val channel = foo () for (x in channel) println (x) }

  3. fun CoroutineScope.foo(): ReceiveChannel<Response> = produce { send( compute ( "A" )) send( compute ( "B" )) send( compute ( "C" )) } A B C foo() Channel<R> send send send A B C main() fun main() = runBlocking { val channel = foo () for (x in channel) println (x) }

  4. fun CoroutineScope.foo(): ReceiveChannel<Response> = produce { send( compute ( "A" )) send( compute ( "B" )) send( compute ( "C" )) } A B C ❌ foo() Channel<R> send send send A B C main() fun main() = runBlocking { val channel = foo () for (x in channel) println (x) }

  5. Channel is hot πŸ”¦

  6. Channel is hot πŸ”¦ fun main() = runBlocking { val channel = foo () for (x in channel) println (x) }

  7. Channel is hot πŸ”¦ fun main() = runBlocking { val channel = foo () // for (x in channel) println (x) }

  8. fun CoroutineScope.foo(): ReceiveChannel<Response> = produce { send( compute ( "A" )) send( compute ( "B" )) send( compute ( "C" )) } foo() Channel main() fun main() = runBlocking { val channel = foo () // for (x in channel) println (x) }

  9. fun CoroutineScope.foo(): ReceiveChannel<Response> = produce { send( compute ( "A" )) send( compute ( "B" )) send( compute ( "C" )) } A foo() πŸ”¦ Channel send main() fun main() = runBlocking { val channel = foo () // for (x in channel) println (x) }

  10. fun CoroutineScope.foo(): ReceiveChannel<Response> πŸ”¦

  11. KOTLIN FLOW Image: Markus Trienke, Sunset over dri6 ice

  12. fun foo(): Flow<Response> = flow { … }

  13. fun foo(): Flow<Response> = flow { … }

  14. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) }

  15. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  16. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  17. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  18. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } foo() main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  19. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } foo() main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  20. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } foo() Flow<R> main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  21. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } foo() Flow<R> main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  22. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } foo() Flow<R> collect main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  23. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } A foo() Flow<R> collect emit main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  24. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } A foo() Flow<R> collect emit A main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  25. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } A foo() Flow<R> collect emit A main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  26. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } A B foo() Flow<R> collect emit emit A main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  27. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } A B foo() Flow<R> collect emit emit A B main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  28. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } A B foo() Flow<R> collect emit emit A B main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  29. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } A B C foo() Flow<R> collect emit emit emit A B main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  30. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } A B C foo() Flow<R> collect emit emit emit A B C main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  31. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } A B C foo() Flow<R> collect emit emit emit A B C main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  32. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } A B C ❌ foo() Flow<R> collect emit emit emit A B C main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  33. fun foo(): Flow<Response> = flow { emit( compute ( "A" )) emit( compute ( "B" )) emit( compute ( "C" )) } A B C ❌ foo() Flow<R> collect emit emit emit A B C main() fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  34. Flow is cold ❄ fun main() = runBlocking { val flow = foo () flow. collect { x -> println (x) } }

  35. Flow is cold ❄ fun main() = runBlocking { val flow = foo () πŸ˜„ // flow. collect { x -> println (x) } }

  36. Flow is declara6ve

  37. Flow is declarative fun foo(): Flow<Response> = flow { emit( compute ( "A" )) Declaration emit( compute ( "B" )) emit( compute ( "C" )) }

  38. fun strings(): Flow<String> = flow { emit( "A" ) emit( "B" ) emit( ”C" ) }

  39. fun strings(): Flow<String> = flow { … } fun foo(): Flow<Response> = strings(). map { name -> compute (name) }

  40. fun strings(): Flow<String> = flow { … } fun foo(): Flow<Response> = strings(). map { name -> compute (name) }

  41. fun strings(): Flow<String> = flow { … } fun foo(): Flow<Response> = strings(). map { name -> compute (name) }

  42. fun strings(): Flow<String> = flow { … } fun foo(): Flow<Response> = Operators strings(). map { name -> compute (name) }

  43. fun foo(): Flow<Response> = Operators flowOf ( "A" , "B" , "C" ). map { name -> compute (name) }

  44. suspend fun foo(): List<Response> = listOf ( "A" , "B" , "C" ). map { name -> Flow vs List compute (name) } fun foo(): Flow<Response> = flowOf ( "A" , "B" , "C" ). map { name -> compute (name) }

  45. suspend fun foo(): List<Response> = listOf ( "A" , "B" , "C" ). map { name -> Runs – Impera:ve Flow vs List compute (name) } fun foo(): Flow<Response> = Defined – Declarative flowOf ( "A" , "B" , "C" ). map { name -> compute (name) } Runs the flow suspend fun <T> Flow<T>.collect(…)

  46. suspend fun foo(): List<Response> = listOf ( "A" , "B" , "C" ). map { name -> Runs – Imperative Flow vs List compute (name) } fun foo(): Flow<Response> = Defined – Declara:ve flowOf ( "A" , "B" , "C" ). map { name -> compute (name) } Runs the flow suspend fun <T> Flow<T>.toList(): List<T>

  47. Execu6on order suspend fun foo(): List<Response> = listOf ( "A" , "B" , "C" ). map { name -> Flow vs List compute (name) } fun foo(): Flow<Response> = flowOf ( "A" , "B" , "C" ). map { name -> compute (name) }

  48. suspend fun foo(): List<Response> = listOf ( "A" , "B" , "C" ). map { name -> Flow vs List compute (name) A B C } fun foo(): Flow<Response> = flowOf ( "A" , "B" , "C" ). map { name -> compute (name) }

  49. suspend fun foo(): List<Response> = listOf ( "A" , "B" , "C" ). map { name -> Flow vs List compute (name) A B C } map fun foo(): Flow<Response> = flowOf ( "A" , "B" , "C" ). map { name -> compute (name) }

  50. suspend fun foo(): List<Response> = listOf ( "A" , "B" , "C" ). map { name -> Flow vs List compute (name) A B C } map A’ B’ C’ fun foo(): Flow<Response> = flowOf ( "A" , "B" , "C" ). map { name -> compute (name) }

  51. suspend fun foo(): List<Response> = listOf ( "A" , "B" , "C" ). map { name -> Flow vs List compute (name) A B C } map A’ B’ C’ fun foo(): Flow<Response> = flowOf ( "A" , "B" , "C" ). map { name -> compute (name) A } A’

  52. suspend fun foo(): List<Response> = listOf ( "A" , "B" , "C" ). map { name -> Flow vs List compute (name) A B C } map A’ B’ C’ fun foo(): Flow<Response> = flowOf ( "A" , "B" , "C" ). map { name -> compute (name) A B } A’ B’

  53. suspend fun foo(): List<Response> = listOf ( "A" , "B" , "C" ). map { name -> Flow vs List compute (name) A B C } map A’ B’ C’ fun foo(): Flow<Response> = flowOf ( "A" , "B" , "C" ). map { name -> compute (name) A B C } React on emi2ed values A’ B’ C’

  54. Flow is reac6ve 🚁 Project RxJava Kotlin Flow Reactor Reactive Streams Specification

  55. Publisher<T> org.reactivestreams Publisher <T>

  56. fun <T : Any> Publisher<T>.asFlow(): Flow<T> org.reactivestreams kotlinx.coroutines.flow Publisher <T> Flow <T>

  57. fun <T : Any> Publisher<T>.asFlow(): Flow<T> org.reactivestreams kotlinx.coroutines.flow Publisher <T> Flow <T> fun <T : Any> Flow<T>.asPublisher(): Publisher<T>

  58. WHY FLOW? What’s the difference?

  59. Flowable<T> Synchronous A fun map(mapper: (T) -> R): Flowable<R> mapper fun flatMapSingle(mapper: (T) -> SingleSource<R>): Flowable<R> A’ Asynchronous

  60. Flowable<T> Synchronous A fun map(mapper: (T) -> R): Flowable<R> mapper fun flatMapSingle(mapper: (T) -> SingleSource<R>): Flowable<R> A’ Asynchronous Synchronous A fun filter(predicate: (T) -> Boolean): Flowable<T> predicate 🀰 A Asynchronous

Recommend


More recommend