Slide 1

Slide 1 text

夏のDispatchers.Main探検 Kotlin愛好会 vol.14 @ウォンテッドリー株式会社

Slide 2

Slide 2 text

自己紹介 Name : Koji Wakamiya Work : Studyplus, inc. Github : @koji-1009 Twitter : @D_R_1009 Android開発メインでやってます 2

Slide 3

Slide 3 text

今日の話のまとめ(TL;DR) 3

Slide 4

Slide 4 text

まとめ ● Dispatchers.MainはLooper.getMainLooper()を CoroutinesContextとして扱えるようにしたもの ● kotlinx.coroutinesパッケージと、kotlinx.coroutines.androidパッケージの 組み合わせによりKotlin Coroutinesの世界とAndroidの世界が繋がれている ● R8によってDispatchres.Mainのinit処理が早くなった!!! 4

Slide 5

Slide 5 text

Kotlin Coroutinesのおさらい 5

Slide 6

Slide 6 text

Kotlin Coroutinesを理解するために ● Kotlin Coroutines ○ sys1yagiさんのブログ ■ Kotlin Fest 2018でコルーチンの話をしてきた ■ Androidと非同期処理 とCoroutine1.0.0 ○ Googleのブログ ■ Android でコルーチン(パート I): 背景を理解する ■ Android のコルーチン(パート II): 使ってみる ■ Android のコルーチン(パート III): 実際の処理 ● CoroutineContext ○ Job, CoroutineContext, CoroutineScopeなどを整理したい ○ 図で理解する Kotlin Coroutine 6

Slide 7

Slide 7 text

CoroutineDispatcher “Base class that shall be extended by all coroutine dispatcher implementations.” ● CoroutineDispatcherはCoroutineが実行環境を司る ○ 単一のスレッドだったり、スレッドプールだったり ○ 実行スケジュールだったり ● Dispatchersクラス経由でよくアクセスする Dispatcher ○ Dispatchers.Default ○ Dispatchers.IO ○ Dispatchers.Unconfined ○ Dispatchers.Main 7

Slide 8

Slide 8 text

Dispatchers.Main 8

Slide 9

Slide 9 text

Dispatchers.Mainとは “A coroutine dispatcher that is confined to the Main thread operating with UI objects. Usually such dispatchers are single-threaded.” ● UI操作のためにMainスレッド上で動作させるための Dispatcher ● プラットフォームごとに実装が異なる ○ JS/Native :Dispatchers.Defaultが指定 ○ JVM :Android/JavaFX/Swingそれぞれのプラットフォーム拡張で対応 9

Slide 10

Slide 10 text

AndroidのDispatchers.Main Kotlin Coroutinesの実行をAndroidのHandler経由で実行させるクラス(モジュール) ● Looper.getMainLooper()したLooperに対するHandlerを生成することで Androidの仕組みを利用したMainスレッドへのアクセスを実現 ● Android SDK 28から以上では Handler.createAsync (API 28で追加)を利用したHandlerに! 10

Slide 11

Slide 11 text

どうやってDispatchers.Mainを見つけるか ● JavaのServiceLoaderクラスを利用 ○ ServiceLoaderはMETA-INFを利用することで、実装クラスを読み込む仕組み ● MainDispatcherLoader(kotlinx.coroutines.internal) が MainDispatcherFactory(kotlinx.coroutines.internal)を継承した AndroidDispatcherFactory(kotlinx.coroutines.android) を読み込む ● 独自のプラットフォームでも MainDispatcherFactoryを継承したクラスを作れば Kotlin CoroutinesのGUI対応ができる!!! 11

Slide 12

Slide 12 text

Dispatchers.Mainの R8による高速化 12

Slide 13

Slide 13 text

Dispatchers.Mainのinit処理時間問題 13 https://github.com/Kotlin/kotlinx.coroutines/issues/878

Slide 14

Slide 14 text

なにが起きていたのか ● ServiceLoaderは使うべきではない……? 14

Slide 15

Slide 15 text

対応 15 https://github.com/Kotlin/kotlinx.coroutines/pull/1304

Slide 16

Slide 16 text

対応 ● R8 v1.6.0~で META-INF/com.android.tools 配下が rule として認識されるように ● META-INFが正しく認識されるようになるため、 ServiceLoaderが正常に動作 ○ ただしちゃんと動くのは Android Studio 3.6.0以上の模様 16

Slide 17

Slide 17 text

今日の話のまとめ(再掲) 17

Slide 18

Slide 18 text

まとめ ● Dispatchers.MainはLooper.getMainLooper()を CoroutinesContextとして扱えるようにしたもの ● kotlinx.coroutinesパッケージと、kotlinx.coroutines.androidパッケージの 組み合わせによりKotlin Coroutinesの世界とAndroidの世界が繋がれている ● R8によってDispatchres.Mainのinit処理が早くなった早くなる!!! いろんな非同期処理の ”Mainスレッド”について書いたブログ -> Androidの非同期処理について自分なりの整理 18