yu-tarrrrの日記

完全に個人の趣味でその時々書きたいことを書く

Quarkus×Kotlinで遊んでみる

はじめに

  • 今回はQuarkusでAPIを立ち上げようと思います
  • どこまで書けるかわかりませんが、とりあえず突き進む予定です

What's Quarkus?

  • KubernetesネイティブなJavaフレームワーク
  • Kubernetesの利用やマイクロサービス・サーバレス化が進み、アプリケーションのコンテナ化が一般的になりつつある現在、Javaの起動速度はネックになる。その問題に対して、QuarkusではGraalVMを用いて作成したNativeバイナリをコンテナ上で起動することにより、Javaの起動時間を劇的に短縮するというもの
  • Red Hatが2019年に発表し、現在は1.2.0が使える(2020年2月時点)

とりあえず遊んでおく

  • 説明は手短に、とりあえず遊んでみるものとします
  • ここから雛形を作って、ダウンロード→任意の場所で展開まではよしなにやってください
  • あとは、./gradlew quarkusDevを叩いてみて、8080にアクセスできれば準備は完了です
  • ちなみに./gradlew quarkusDevを叩く場合は、ホットリロードが走るので再コンパイルは不要(ここら辺は、Spring使ってた人間からしてみると痒いところに手が届く感じがして良いです)

あとは、基本的にはJAX-RSの書き方に準拠していく感じ

import javax.ws.rs.GET
import javax.ws.rs.Path
import javax.ws.rs.Produces
import javax.ws.rs.QueryParam
import javax.ws.rs.core.MediaType

@Path("/hello")
class ExampleResource {

    @GET
    @Path("world")
    @Produces(MediaType.TEXT_PLAIN)
    fun hello(@QueryParam(value = "name") name: String) :String = "hello ${name}"
}

ちなみに、ここら辺で気付いたのですが、

INFO  [io.qua.dev] (vert.x-worker-thread-3) Changed source files detected, recompiling 
INFO  [io.quarkus] (vert.x-worker-thread-3) Quarkus stopped in 0.000s
INFO  [io.quarkus] (vert.x-worker-thread-3) Quarkus 1.2.0.Final started in 0.189s. Listening on: http://0.0.0.0:8080
INFO  [io.quarkus] (vert.x-worker-thread-3) Profile dev activated. Live Coding activated.
INFO  [io.quarkus] (vert.x-worker-thread-3) Installed features: [cdi, jdbc-mysql, resteasy]
INFO  [io.qua.dev] (vert.x-worker-thread-3) Hot replace total time: 0.282s 

こんな感じで、アクセスが来る→止まる→差分が検知される→再コンパイルみたいな挙動を自動でやってくれるみたいです。 なので、アクセスしない限りはリスタートしないので、イメージしてたホットリロードではなかったです。

ここで新たな疑問が・・・

  • build.gradleにいれた覚えのないvert.xのworkerがなぜか動いてるという・・・
plugins {
    id 'org.jetbrains.kotlin.jvm' version "1.3.41"
    id "org.jetbrains.kotlin.plugin.allopen" version "1.3.41"
    id 'io.quarkus'
}

repositories {
     mavenLocal()
     mavenCentral()
}

dependencies {
    implementation 'io.quarkus:quarkus-jdbc-mysql'
    implementation 'io.quarkus:quarkus-kotlin'
    implementation enforcedPlatform("${quarkusPlatformGroupId}:${quarkusPlatformArtifactId}:${quarkusPlatformVersion}")
    implementation 'io.quarkus:quarkus-resteasy'
    implementation 'org.jetbrains.kotlin:kotlin-stdlib-jdk8'

    testImplementation 'io.quarkus:quarkus-junit5'
    testImplementation 'io.rest-assured:rest-assured'
}

group 'org.acme'
version '1.0.0-SNAPSHOT'

quarkus {
    setOutputDirectory("$projectDir/build/classes/kotlin/main")
}

quarkusDev {
    setSourceDir("$projectDir/src/main/kotlin")
}

allOpen {
    annotation("javax.ws.rs.Path")
    annotation("javax.enterprise.context.ApplicationScoped")
    annotation("io.quarkus.test.junit.QuarkusTest")
}

java {
    sourceCompatibility = JavaVersion.VERSION_1_8
    targetCompatibility = JavaVersion.VERSION_1_8
}

compileKotlin {
    kotlinOptions.jvmTarget = JavaVersion.VERSION_1_8
    kotlinOptions.javaParameters = true
}

compileTestKotlin {
    kotlinOptions.jvmTarget = JavaVersion.VERSION_1_8
}
  • で、この記事に辿り来ました
  • どうやら、Quarkus の HTTP レイヤーは Vert.x ベースになっているそうです
  • (過去の経験から、worker数とか知っておかないと怖いなと思った次第です)
  • なのでチューニングしたければ、worker数は20で設定されているようなので(デフォルト)、そこをいじれば良さそう。(因みに、設定できる項目が見れるのはここにあります)
  • src/main/resources/application.propertiesの設定値を修正すれば良さそう

因みに

  • ./mvnw quarkus:generate-configを叩けばサンプルのapplication.propertiesを落として来れるのですが、全体で1300行くらいあるので必要ない場合はあまりおすすめできないかと(因みに、gradlewで叩こうとしたのですが、なぜかコケたので断念しました)
  • SpringだとIntelliJと相性が良く、application.properties書く際に、いい感じに補完してくれてたので、そこらへんがないのは仕方ないとはいえ残念な感じ

まとめ

  • 次回はDBにつないで簡単なCRUDAPIを作りたい

良かったところ

  • Clientがちゃんと揃っていて気軽に始めやすい
  • 起動は確かに早い
  • あと、ホットリスタートがある

微妙なところ

  • GradleがまだPreviewなところ
  • Java以外のLanguageがまだPreviewなところ
  • 公式みるとわかるのですが、Previewが多い印象(とはいえ、まだversion 1.2.0なので)