KotlinとThymeleafでハマったこと


背景

  • 前回書いた記事でThymeleafを使った簡単なアプリケーションを実装した
  • その際にisNewというbooleanの変数をDTOに定義して、Thymeleafからアクセスしようとしたが、なぜか取得できなかった

ソース

  • ソースは以下の感じ
  • isNewというフラグで画像の表示をするか判定してるだけ
top.html
<div style="float: left; margin: 5px" th:each="image, index:${imageResources}">
    <span th:if="${image.isNew}">
        <img th:src="@{img/new.png}" style="width:30px; height:30px">
    </span>

  • 下がtop画面に表示させるためのレスポンスクラス
LgtmTopResponse.kt
class LgtmTopResponse {
    var imageUrl = String()
    var imageName = String()
    var imageLgtmUrl = String()
    var updateDatetime = Date()
    var isNew = false

    fun buildWithEntity(lgtmEntity: LgtmEntity,baseDate :Date) : LgtmTopResponse{
        return LgtmTopResponse().apply {
            imageUrl = lgtmEntity.imageUrl
            imageName = lgtmEntity.imageName
            imageLgtmUrl = lgtmEntity.imageLgtmUrl
            updateDatetime = lgtmEntity.updateDatetime
            isNew = lgtmEntity.updateDatetime.after(baseDate)
        }
    }
}

このまま実行すると怒られた

原因と対策

  • 原因としては、kotlinでisNewというプロパティがコンパイルを実行すると、newという変数名に変換されてしまうっぽい
  • なので、Thymeleafからはisを外したプロパティ名でアクセスすれば動く
  • もしくはメソッドアクセスみたいな感じで、isNew()でも動くっぽい
  • どっちで書くのが良いのかはまだわかってないです

ソースを修正

top.html
<span th:if="${image.new}">
    <img th:src="@{img/new.png}" style="width:30px; height:30px">
</span>

または、こっち

top.html
<span th:if="${image.isNew()}">
    <img th:src="@{img/new.png}" style="width:30px; height:30px">
</span>

まとめ

  • Javaでつくったアプリケーションのサーバー側をKotlinに書き換える際に、フロントを全くいじらなくて良いという訳ではなさそう
  • is〇〇って名前はちょいちょい使うので、これはちょっとイケてないなーと思った
  • とはいえ、Kotlinはやっぱり楽しい

参考リンク

Thymeleaf で isXxx プロパティを参照するとエラーになる