kdnakt blog

hello there.

第49回Kotlin dojoを開催した

今週は第49回を開催しました。引き続きKotlin Hands-onをすすめています。

 

前回の様子はコチラ↓ 

kdnakt.hatenablog.com

 

 

[第49回の様子]

2021/1/26に第49回を開催した。

 

参加メンバーは自分をいれて4名。先週の終了時点比でいうと2.5倍に増加しているw

2020年に何度か参加してくれていて、今年初参加というメンバーもいた。継続して参加してくれてありがたい。

 

勉強会本編の内容としては、Introduction to Coroutines and Channelsハンズオンを今回から進めた。第1章からはじめて、第2章の途中までを学んだ。

 

[学んだことや疑問点]

  • Introduction to Coroutines and Channels: 1. Introduction
    • サスペンド関数の使い方、なぜ必要か、コルーチンとチャンネルの使い方を学べるハンズオンらしい
    • プロジェクトのセットアップはいつもどおりGitHubからソースコードをクローンするだけ
    • と思いきや、GitHubAPIを利用するのに、GitHubトークンが必要になるらしい
    • クローンしたソースコードトークンをセットして動かすと、GUIGitHub APIの結果を確認できた
    • ネットワーク通信にはRetrofitというHTTPクライアントライブラリを利用している
    • ブロッキングモードを利用したので、ロード処理が終わるまでやや画面が固まっていた

f:id:kidani_a:20210128004938p:plain

  • Introduction to Coroutines and Channels: 2. Blocking request
    • Retrofitを利用したブロッキング処理の実装を見ていく
    • インターフェースでAPIを定義して、ベースURLを与えて実体を作るらしい。以下は公式サイトのJavaのサンプル。
public interface GitHubService {
  @GET("users/{user}/repos")
  Call<List<Repo>> listRepos(@Path("user") String user);
}

Retrofit retrofit = new Retrofit.Builder()
    .baseUrl("https://api.github.com/")
    .build();

GitHubService service = retrofit.create(GitHubService.class);

Call<List<Repo>> repos = service.listRepos("octocat");
    • 本ハンズオンでのKotlinからのRetrofit利用は以下のような感じ
interface GitHubService {
    @GET("orgs/{org}/repos?per_page=100")
    fun getOrgReposCall(
        @Path("org") org: String
    ): Call<List<Repo>>

    @GET("repos/{owner}/{repo}/contributors?per_page=100")
    fun getRepoContributorsCall(
        @Path("owner") owner: String,
        @Path("repo") repo: String
    ): Call<List<User>>
}

fun loadContributorsBlocking(service: GitHubService, req: RequestData) : List<User> {
    val repos = service
        .getOrgReposCall(req.org)
        .execute()
        .also { logRepos(req, it) }
        .body() ?: listOf()

    return repos.flatMap { repo ->
        service
            .getRepoContributorsCall(req.org, repo.name)
            .execute()
            .also { logUsers(repo, it) }
            .bodyList()
    }.aggregate()
}
    • .body() ? listOf()で空リストを返す部分が繰り返されるので拡張関数としてbodyList()が追加で定義されていた
    • 以前のKotlin dojoでも話題になった、スコープ関数5兄弟の1人alsoが登場している
    • 以下の記事を参考にすると、たしかに「ついでに」ログを残しているのでこの場合はalsoが適切そう。

qiita.com

    • 英語の意味的にも他のスコープ関数(runとかlet)だとやや可読性が下がる気がする(applyはありかも?)
    • スコープ関数の使い分けはまだ修行が必要そう
    • flatMap()Koansの問題集で出てきたときは結構難しく感じたけど、実際に使ってるのを見るとそれほどでもないかも。

 

[まとめ]

モブプログラミング・スタイルで、Introduction to Coroutines and Channelsハンズオンを進めた。

Ktorとはまた一味違うRetrofitというライブラリに触れることができた。

スコープ関数alsoを実際に利用している場面を見て、少しだけ理解が深まった。

 

今週の進捗は以下のプルリクエストにまとまっている。

github.com