LoginSignup
4
4

More than 5 years have passed since last update.

Slick+MySQLでdatetimeやtimestampをjava.time.*に変換したい【Slick3.3以降】

Posted at

はじめに

この間怒りに任せてあげたSlickでいつの間にかjava.time.*がサポートされてた話ではMySQLのdatetimetimestampjava.time.LocalDateTimeに相互変換されませんって話でした。
しかも以前はサポート対象外だったおかげて暗黙の変換を書いておけば問題なかったんですが、3.3以降、自分の環境ではjava.time.*系の変換を書いちゃうとどっかで衝突すんのかコンパイルが通らなくなってしまいました(上記前記事参照)。

という訳で今回はどうにかして変換できるようにしてみます。

環境

scala: 2.12
slick: 3.3

型を作ってしまおう

しょうがないので間に型を咬ませます。
代表してdatetimeをサポートしてみます。

case class MySQLDateTime(value: String) {

 def toLocalDateTime: LocalDateTime =
    LocalDateTime.parse(value, DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"))
}

回りくどい気もしますが、値としてdatetimeStringで保持し、LocalDateTimeとして出力できるようにしています。

テーブルではこんな感じ

class TestTable(tag: Tag) extends Table[Test](tag, "test") {
  // 抜粋
  def testDate = column[MySQLDateTime]("test_date")
  // 抜粋
}

このままでは当然MySQLDateTime型は変換できないのでコンパイルは通りません。

暗黙の変換

上記テーブルに下記の暗黙の変換を追加します。


implicit lazy val mySqlDateTimeType: JdbcType[MySQLDateTime] with BaseTypedType[MySQLDateTime] =
  MappedColumnType.base[MySQLDateTime, java.sql.Timestamp](
    t => java.sql.Timestamp.valueOf(t.value),
    u => MySQLDateTime(u.toLocalDateTime.format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")))
  )

テーブルからはjava.sql.Timestampとして受けて相互変換可能としています。DateTimeFormatter...云々はどこぞに固定値として生やした方が良いでしょう。

おわりに

timestampdatetimeも同様に書くことができると思います。

4
4
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
4
4