たごもりすメモ

コードとかその他の話とか。

DropwizardとShadow jarの話

AWS Lambda用にshadow jarをビルドしてたリポジトリで、別のデーモンプロセス*1をDropwizardベースにすることにして依存関係やビルド方法などを書き換えていったところ、設定ファイルに書かれてるLog appenderが見えない、みたいなエラーが出て起動に失敗するという状況に。手元で./gradlew runしたときはうまくいくんだけどサーバにデプロイしたらダメ。

io.dropwizard.configuration.ConfigurationParsingException: /opt/myapp/config.yaml has an error:
   * Failed to parse configuration at: logging.appenders.[0]; Could not resolve type id 'console' as a subtype of `io.dropwizard.logging.AppenderFactory<ch.qos.logback.classic.spi.ILoggingEvent>`: known type ids = [] (for POJO property 'appenders')
  at [Source: UNKNOWN; line: -1, column: -1] (through reference chain: com.myapp.MyAppConfiguration["logging"]->io.dropwizard.logging.DefaultLoggingFactory["appenders"]->java.util.ArrayList[0])
         at io.dropwizard.configuration.ConfigurationParsingException$Builder.build(ConfigurationParsingException.java:278)
         at io.dropwizard.configuration.BaseConfigurationFactory.build(BaseConfigurationFactory.java:157)
...

なんかこんな感じのスタックトレースが出る。

調べてみたらDropwizardによる実装の探索とshadowが衝突しているっぽい。このへんのコメントを参考にした。
で、手元はGradleはKotlin DSLで書かれてるので、このコメントを参考にえいやとbuild.gradle.ktsに以下のようなのを追加。

import com.github.jengelman.gradle.plugins.shadow.tasks.ShadowJar

// ...

tasks {
    named<ShadowJar>("shadowJar") {
        archiveBaseName.set("stream-processing-shadow")
        mergeServiceFiles()
        manifest {
            attributes(mapOf("Main-Class" to application.mainClassName))
        }
    }
}

これでうまくいった。めでたしめでたし。

*1:同じリポジトリの別Main classを使う