この記事はkdnaktの1人 Advent Calendar 2020の5日目の記事です。
2020年は会社でKotlin dojoを主催して週1回30分Kotlinと戯れていました。12月はその集大成ということで、KotlinでHTTPサーバーを作ってみたいと思います。どこまでできるか、お楽しみ……。
[パッケージを分割する]
現在のソースコードは、ビルドされたバイナリファイルを覗くとこのようになっています。
$ tree -I build . ├── build.gradle.kts ├── settings.gradle.kts └── src └── nativeMain └── kotlin └── hello.kt
現時点ではhello.kt
の1ファイルしかソースコードがありませんが、プロダクトバックログに記載したとおり、設定ファイルの読み込みやTLS対応など、複数の機能を追加する予定があります。しかし、このままではすべてのソースコードをsrc/nativeMain/kotlin
ディレクトリの直下に配置せざるをえません。数年Javaをやっている身としては、やはり各ファイルの責務に応じて、パッケージに分割したくなります。
Kotlinでも、Javaと同様にpackage <パッケージ名>
という形でパッケージ名を宣言することができるので、hello.kt
ファイルをcom.kdnakt.httpd
パッケージに配置します。
Packages and Imports - Kotlin Programming Language
まず、必要なディレクトリを作成し、hello.kt
ファイルを移動させます。
$ cd src/nativeMain/kotlin $ mkdir -p com/kdnakt/kttpd $ mv hello.kt com/kdnakt/kttpd/
この時点で、プロジェクトのディレクトリ構成は次のようになっています。
$ tree -I build . ├── build.gradle.kts ├── settings.gradle.kts └── src └── nativeMain └── kotlin └── com └── kdnakt └── kttpd └── hello.kt
つぎに、hello.kt
を編集してパッケージ名を宣言します。
package com.kdnakt.kttpd // この行を追加 fun main() { println("Hello Kotlin/Native!") }
プロジェクトのトップディレクトリに戻り、ビルドを実行してみます。
$ cd ../../../ $ gradle nativeBinaries Starting a Gradle Daemon (subsequent builds will be faster) > Configure project : Kotlin Multiplatform Projects are an Alpha feature. See: https://kotlinlang.org/docs/reference/evolution/components-stability.html. To hide this message, add 'kotlin.mpp.stability.nowarn=true' to the Gradle properties. > Task :linkDebugExecutableNative FAILED e: Could not find 'main' in '<root>' package. FAILURE: Build failed with an exception. * What went wrong: Execution failed for task ':linkDebugExecutableNative'. > Compilation finished with errors * Try: Run with --stacktrace option to get the stack trace. Run with --info or --debug option to get more log output. Run with --scan to get full insights. * Get more help at https://help.gradle.org Deprecated Gradle features were used in this build, making it incompatible with Gradle 7.0. Use '--warning-mode all' to show the individual deprecation warnings. See https://docs.gradle.org/6.7.1/userguide/command_line_interface.html#sec:command_line_warnings BUILD FAILED in 26s 2 actionable tasks: 2 executed
エラーが出てビルドが失敗してしまいました。e: Could not find 'main' in '<root>' package.
とあるので、エントリーポイントとなるmain()
関数をルートパッケージから別の場所へ移動してしまったことが原因のようです。
Introduction to Kotlin/Nativeというハンズオンを確認すると、build.gradle
ファイルのexecutable
タスク部分にentryPoint
が記載されています。この点が現在のプロジェクトで利用しているbuild.gradle.kts
ファイルと異なるので、以下のようにentryPoint
を追加します。executable()
の丸カッコ()
が波カッコ{}
になっている点に注意が必要です。
// 修正前 kotlin { macosX64("native") { binaries { executable() } } } // 修正後 kotlin { macosX64("native") { binaries { executable { entryPoint = "com.kdnakt.kttpd.main" } } } }
改めてコマンドを実行すると、今度はgradle nativeBinaries
コマンドが成功しました。
$ gradle nativeBinaries > Configure project : Kotlin Multiplatform Projects are an Alpha feature. See: https://kotlinlang.org/docs/reference/evolution/components-stability.html. To hide this message, add 'kotlin.mpp.stability.nowarn=true' to the Gradle properties. Deprecated Gradle features were used in this build, making it incompatible with Gradle 7.0. Use '--warning-mode all' to show the individual deprecation warnings. See https://docs.gradle.org/6.7.1/userguide/command_line_interface.html#sec:command_line_warnings BUILD SUCCESSFUL in 39s 3 actionable tasks: 3 executed
これでパッケージを分割しながらKotlin/Nativeの開発がすすめられそうです。