前人未踏の領域へ Androidアプリ開発編

Androidアプリ開発に関する調査メモ置き場。古い記事にはアプリ以外も含まれます。

KMMチュートリアル中にハマった箇所

内容

Kotlinの公式サイトにあるKMMのチュートリアル
Get started with Kotlin Multiplatform Mobile を進めていくうち、2023年1月20日現在で動かない箇所があったのでそのメモと対策。ある時期だけ意味をなすと思われる消費期限のありそうな記事。あと使用しているAndroid Studioによっても状況が異なるかもしれない。

対応

1. プロジェクトテンプレートとチュートリアルで関数名が異なる

Create the project from a template のところでKotlin Multiplatform Appを選択してプロジェクトを生成すると Greeting.kt というファイルが同時にが作られるんだけど、関数名が greet になっている。

class Greeting {
    private val platform: Platform = getPlatform()

    fun greet(): String {
        return "Hello, ${platform.name}!"
    }
}

だけどUpdate your applicationではgreeting で話が進んでいくので、まるごとコピペすると別ファイルがエラーになる。

class Greeting {
    private val platform: Platform = getPlatform()

    fun greeting(): String {
        return "Guess what it is! > ${platform.name.reversed()}!"
    }
}

2. KtorをインポートするとiOSでビルドが通らなくなる

Ktor(https://kotlinlang.org/docs/multiplatform-mobile-upgrade-app.html#ktor)のところで必要モジュールを追加すると、iosAppをビルドしようとした時点でエラーが発生するようになる。ログを見るとバージョンの依存関係の問題ということが分かる

> Task :shared:linkDebugFrameworkIosSimulatorArm64 FAILED
e: Module "io.ktor:ktor-io (io.ktor:ktor-io-iossimulatorarm64)" has a reference to symbol kotlin.ranges/contains|-4666807430820256279[0]. Neither the module itself nor its dependencies contain such declaration.

This could happen if the required dependency is missing in the project. Or if there is a dependency of "io.ktor:ktor-io (io.ktor:ktor-io-iossimulatorarm64)" that has a different version in the project than the version that "io.ktor:ktor-io (io.ktor:ktor-io-iossimulatorarm64): 2.2.1" was initially compiled with. Please check that the project configuration is correct and has consistent versions of all required dependencies.

The list of "io.ktor:ktor-io (io.ktor:ktor-io-iossimulatorarm64): 2.2.1" dependencies that may lead to conflicts:
1. "stdlib: 1.7.10" (was initially compiled with "stdlib: 1.6.21")
2. "org.jetbrains.kotlin.native.platform.CoreFoundation: 1.7.10" (was initially compiled with "org.jetbrains.kotlin.native.platform.CoreFoundation: 1.6.21")
3. "org.jetbrains.kotlin.native.platform.darwin: 1.7.10" (was initially compiled with "org.jetbrains.kotlin.native.platform.darwin: 1.6.21")
4. "org.jetbrains.kotlin.native.platform.iconv: 1.7.10" (was initially compiled with "org.jetbrains.kotlin.native.platform.iconv: 1.7.20")
5. "org.jetbrains.kotlin.native.platform.posix: 1.7.10" (was initially compiled with "org.jetbrains.kotlin.native.platform.posix: 1.6.21")
6. "org.jetbrains.kotlinx:atomicfu (org.jetbrains.kotlinx:atomicfu-iossimulatorarm64): 0.18.5" (was initially compiled with "org.jetbrains.kotlinx:atomicfu (org.jetbrains.kotlinx:atomicfu-iossimulatorarm64): 0.17.3")

Kotlin側のバージョンを下げると色々と問題がありそうなのでktorVersionを2.0.3に下げるとエラーはなくなるのだが、結局すぐ次のiOS APP(https://kotlinlang.org/docs/multiplatform-mobile-upgrade-app.html#ios-app) というステップでエラーになる。(検索にヒットするかもしれないのでログを貼っておく)

Uncaught Kotlin exception: kotlin.native.IncorrectDereferenceException: illegal attempt to access non-shared <object>@3fcc308 from other thread
    at 0   shared                              0x10558391b        kfun:kotlin.Throwable#<init>(kotlin.String?){} + 95 (/opt/buildAgent/work/67fbc2b507315583/kotlin/kotlin-native/runtime/src/main/kotlin/kotlin/Throwable.kt:24:37)
    at 1   shared                              0x10557cfef        kfun:kotlin.Exception#<init>(kotlin.String?){} + 91 (/opt/buildAgent/work/67fbc2b507315583/kotlin/kotlin-native/runtime/src/main/kotlin/kotlin/Exceptions.kt:23:44)
    at 2   shared                              0x10557d223        kfun:kotlin.RuntimeException#<init>(kotlin.String?){} + 91 (/opt/buildAgent/work/67fbc2b507315583/kotlin/kotlin-native/runtime/src/main/kotlin/kotlin/Exceptions.kt:34:44)
    at 3   shared                              0x10558f24f        kfun:kotlin.native.IncorrectDereferenceException#<init>(kotlin.String){} + 91 (/opt/buildAgent/work/67fbc2b507315583/kotlin/kotlin-native/runtime/src/main/kotlin/kotlin/native/Runtime.kt:34:36)
    at 4   shared                              0x105591d73        ThrowIllegalObjectSharingException + 423 (/opt/buildAgent/work/67fbc2b507315583/kotlin/kotlin-native/runtime/src/main/kotlin/kotlin/native/concurrent/Internal.kt:115:11)

結局色々と調べていくと、Kotlinのバージョンが1.7.20未満だと、メモリ管理の方法が異なる関係でエラーが発生していたようだ。

プロジェクト直下のbuild.gradle.ktsが以下のようになっていた。

plugins {
    //trick: for the same plugin versions in all sub-modules
    id("com.android.application").version("7.4.0").apply(false)
    id("com.android.library").version("7.4.0").apply(false)
    kotlin("android").version("1.7.10").apply(false)
    kotlin("multiplatform").version("1.7.10").apply(false)
}

これを以下のように編集する

plugins {
    //trick: for the same plugin versions in all sub-modules
    id("com.android.application").version("7.3.1").apply(false)
    id("com.android.library").version("7.3.1").apply(false)
    kotlin("android").version("1.7.21").apply(false)
    kotlin("multiplatform").version("1.7.21").apply(false)
}

すると今度はAndroid側が動かくなるのでandroidApp/build.gradle.ktskotlinCompilerExtensionVersion1.3.2にしてやる必要がある

    composeOptions {
        kotlinCompilerExtensionVersion = "1.3.2"
    }

雑感

  • Android Studio Electric Eelでも動く
  • 多分他の動く組み合わせもある
  • チュートリアルとサンプルコードは動くうちに叩け。
  • 手間がかかった割にこの記事は誰の役にも立たないかもしれない

参考