Upgrade to Pro — share decks privately, control downloads, hide ads and more …

jackson-module-kotlinを読もう!

wrongwrong
April 15, 2022
1.1k

 jackson-module-kotlinを読もう!

Server-Side Kotlin Meetup vol.2

wrongwrong

April 15, 2022
Tweet

Transcript

  1. jackson-module-kotlin
    を読もう!
    1

    View full-size slide

  2. 始める前に
    この発表では解説に jackson-module-kotlin
    リポジトリのコードを利用します
    リポジトリ & 使用するブランチのURLは下記の通りです
    https://github.com/FasterXML/jackson-module-kotlin/tree/2.13
    2

    View full-size slide

  3. 自己紹介
    宮田 木織
    株式会社justInCaseTechnorogiesバックエンドエンジニア
    アウトプットしているアカウント
    Qiita: @wrongwrong
    GitHub: k163377
    OSS活動
    去年から jackson-module-kotlin
    へしばしばコントリビュートしています
    2021年下半期のコミット数世界一でした
    最近は kotlin-reflect
    の value class
    絡みのバグ修正にも携わりました
    3

    View full-size slide

  4. Jackson
    /jackson-module-kotlin
    とは
    Jackson
    は、 Java
    向けでは世界で最も使われている JSON
    ライブラリの一つ
    外部モジュールを使えば CSV
    や XML
    といったフォーマットも処理可能
    jackson-module-kotlin
    は、 Jackson
    を Kotlin
    で利用するためのモジュール
    以下のような機能を提供している
    コンストラクタ呼び出しでのデシリアライズ
    Kotlin
    固有の型に関するシリアライズ/デシリアライズ
    Jackson
    を Kotlin
    から扱いやすくする関数類
    特に Kotlin
    で SpringBoot
    を使う場合かなり利用機会がある
    4

    View full-size slide

  5. 所で……
    jackson-module-kotlin
    のコードを読んだことは有りますか?
    ライブラリを使いこなすには、読んでみるのが効果的です
    設定可能な項目の把握
    挙動をカスタムする際に利用できそうな機能の把握
    一方、ライブラリのコードを事前知識や目標無しで読み始めるのは結構大変です
    この発表では、ざっくり jackson-module-kotlin
    を読んでみたい方向けに、何がどこ
    に書かれているかや、具体的な処理内容について軽く解説します
    5

    View full-size slide

  6. この発表で紹介する内容
    KotlinModule.kt
    / KotlinFeature.kt
    kotlin-module
    の持っている機能や設定項目を俯瞰できる
    KotlinNamesAnnotationIntrospector.kt
    kotlin-module
    の重要な機能を多く実装している
    (コントリビュートしてみたい方向けのおまけ)
    kotlin-module
    のビルド・テスト方法について
    自分がどのようにコードを読んでいるか
    すぐ直せそうな問題
    6

    View full-size slide

  7. 発表形式について
    ここからは、実際のコードを中心に、スライドは補助資料として発表していきます。
    7

    View full-size slide

  8. KotlinModule.kt
    受け取った設定に基づき Jackson
    ( ObjectMapper
    )に様々な機能を登録するクラス
    kotlin-module
    にどのような設定ができるか/ Jackson
    のどのような機能を利用して
    いるか俯瞰できる
    ここでは設定可能な項目や登録されている機能の一部を紹介する
    8

    View full-size slide

  9. KotlinModule.kt
    KotlinFeature.kt
    KotlinModule.Builder
    への設定項目
    設定可能な項目の例
    値が null
    の場合にデフォルト値を利用する
    デシリアライズ時に Collection
    要素の nullability
    を厳密にチェックする
    KotlinModule.Builder
    設定を登録した上で KotlinModule
    を生成するビルダー
    設定可能な項目の例
    KotlinFeature
    の有効/無効化
    リフレクション処理のキャッシュ量の上限値
    9

    View full-size slide

  10. KotlinModule.kt
    setupModule
    受け取った設定に基づき、各機能のインスタンス生成・登録を行う関数
    登録されている機能の例
    デシリアライズ時のパラメータ読み出し/関数呼び出しの制御関連
    ( KotlinInstantiators
    )
    Kotlin
    固有の型に関するシリアライズ・デシリアライズ設定関連
    ( ~Deserializers
    / ~Serializers
    )
    ObjectMapper
    に登録している機能を俯瞰できる
    10

    View full-size slide

  11. KotlinNamesAnnotationIntrospector.kt
    AnnotationIntrospector
    は様々なカスタム挙動を実装するためのクラス
    アノテーションに関係なく、シリアライズ・デシリアライズ問わず、多くの挙動を
    カスタムできる
    kotlin-module
    でも多くの重要な機能を実装している
    ここでは実装されている機能の一部を紹介する
    11

    View full-size slide

  12. KotlinNamesAnnotationIntrospector.kt
    Kotlin
    上のis~
    というプロパティのシリアライズ結果を自然にする処理
    Jackson
    のデフォルト挙動では、 isFoo()
    という getter
    は foo
    プロパティになる
    これは Kotlin
    から見ると不自然な挙動
    findRenameByField
    getter
    から作られたプロパティ名をフィールド名から補正するための関数
    is
    から始まるプロパティ名だった場合にそれが消えないようにしている
    12

    View full-size slide

  13. KotlinNamesAnnotationIntrospector.kt
    自然にコンストラクタを呼び出してデシリアライズするための処理
    Jackson
    単体では Kotlin
    上のプライマリコンストラクタ認識してデシリアライズに用いる
    ようなことはできないため、カスタム挙動が実装されている。
    hasCreatorAnnotation
    主にプライマリコンストラクタをデシリアライズに利用するための関数
    JsonCreator
    アノテーションが付与されていることにしている
    findKotlinParameterName
    Kotlin
    上の引数名を Jackson
    から利用するため処理
    13

    View full-size slide

  14. KotlinNamesAnnotationIntrospector.kt
    補足
    KotlinAnnotationIntrospector.kt
    も AnnotationIntrospector
    を継承している
    14

    View full-size slide

  15. まとめ
    この発表では、ざっくり jackson-module-kotlin
    を読んでみたい方向けに幾つかのコ
    ードを解説しました
    jackson-module-kotlin
    のコードを読んでみるのは、 Jackson
    を使いこなす上で非
    常に役に立つと思います
    紹介しきれなかったコードも多くあるので是非1度読んでみて下さい!
    特に役立ちそう: Extensions.kt
    コントリビュートしてみたい方も是非!
    15

    View full-size slide

  16. We are hiring!
    justInCaseTechnologiesでは保険APIサーバーを開発するバックエンドエンジニアを募集
    しています
    技術スタック: Kotlin
    / Spring Webflux
    / AWS
    「助けられ、助ける喜びを、全ての人へ。」をテーマに、保険業務の効率化によってみ
    なさんによりよい保険を届けます
    詳しくはホームページから!
    採用全般
    エンジニア求人一覧
    16

    View full-size slide

  17. jackson-module-kotlin
    をビルドしてテストを走らせるまで
    前提
    Intellij IDEA
    や Java
    ・ Maven
    を動かすための環境は構築済みとする
    リポジトリは fork
    ・ clone
    済みとする
    https://github.com/FasterXML/jackson-module-kotlin
    Maven
    のコマンドは mvn ~~
    で記述する
    18

    View full-size slide

  18. jackson-module-kotlin
    をビルドしてテストを走らせるまで
    テスト実行
    mvn verify
    で全てのテストが実行できる
    Windows
    の場合改行コード問題で一部テストが失敗する
    補足: IDEA
    から初回テストを実行する
    mvn replacer:replace
    を先に実行(← ここ重要!)
    初回は必要なコードがローカルに生成されていないため
    mvn verify
    で実行した場合、これも自動で実行されている
    IDEA
    からテストを実行
    e.g. テスト横の再生ボタンを押す
    19

    View full-size slide

  19. jar
    を生成する
    mvn jar:jar
    で、 ${
    プロジェクトルート}/target
    配下に jackson-module-
    kotlin-${
    バージョン}.jar
    が出力される
    まだ公開されていない SNAPSHOT
    などは、ローカルで生成した jar
    を使って検証で
    きる
    20

    View full-size slide

  20. 自分がどのようにコードを読んでいるか
    1. まずそのまま読んでみる
    2. その処理を消すか編集してテスト結果がどう変化するか見る
    3. 地道にドキュメント漁りと挙動実験をする
    21

    View full-size slide

  21. すぐ直せそうな問題
    OSS
    にコントリビュートしてみたい方向けに、軽微で簡単そうな問題を幾つか示します
    以下の点にご注意ください
    提示する内容は発表者の認識であるため、実際に対応する場合必ず検証すること
    jackson-module-kotlin
    に関しては、 CLA
    の提出が必要なこと
    メンテナが半分失踪中なため、レビューがいつになるか分からないこと
    22

    View full-size slide

  22. すぐ直せそうな問題(1)
    Extensions.kt
    fun foo(...) = Unit.apply { ... }
    となっている関数の = Unit.apply

    消せる
    KotlinDeserializers.kt
    type.isInterface
    の判定は消せる
    その後に class
    の一致を判定しているので interface
    比較は無意味
    KotlinFeature.kt
    BitSet
    関連の計算が非効率
    23

    View full-size slide

  23. すぐ直せそうな問題(2)
    KotlinKeyDeserializers.kt
    unsigned integers
    系の処理では super.deserializeKey
    するより目的の値に
    直接パースした方が効率的
    パースには StdKeyDeserializer
    の _parseInt
    のような関数を利用する
    KotlinModule.kt
    ClosedRange
    に対してだけ Mixin
    を登録する形にできる
    登録されている ~Range
    は全て ClosedRange
    を継承しており、特別なプロパ
    ティも無い
    KotlinNamesAnnotationIntrospector.kt
    このクラスを KotlinAnnotationIntrospector
    にまとめてもテスト結果は変化し
    ないため、まとめられるかも
    (これは結構検証が難しいかもしれない)
    24

    View full-size slide