tanacasinoのメモ

what are you waiting for ?

Slick で 複数のカラムを同時にアップデートする方法

表題の件が、パッと見てもわからなかったので調べたのでメモ。

GitBucketのバグ修正で、とあるカラムをとあるカラムと同様に更新するというコードを書いたのですが、同時に更新する方法がさっとわからなかったので、それぞれのカラムを別々のクエリで更新するというしょうもないことをしてしまったので、反省を込めてメモ。(せっかくなんでリリースに間に合わせたくてとりあえずバグが直ってて動くことを優先した・・・)

Before

def updateCommitIdTo(owner: String, repository: String, issueId: Int, commitIdTo: String): Unit =
  Query(PullRequests).filter(_.byPrimaryKey(owner, repository, issueId)).map(_.commitIdTo).update(commitIdTo)

def updateCommitIdFrom(owner: String, repository: String, issueId: Int, commitIdFrom: String): Unit =
  Query(PullRequests).filter(_.byPrimaryKey(owner, repository, issueId)).map(_.commitIdFrom).update(commitIdFrom)

After

def updateCommitId(owner: String, repository: String, issueId: Int, commitIdTo: String, commitIdFrom: String): Unit =
  Query(PullRequests).filter(_.byPrimaryKey(owner, repository, issueId))
                     .map(pr => pr.commitIdTo ~ pr.commitIdFrom)
                     .update((commitIdTo, commitIdFrom))

多分あってるはず。 言葉で説明すると、 map で更新するカラムを選択するが、単一カラムでない場合は、~ でつなげたオブジェクトを返す必要があり(.map(pr => pr.commitIdTo ~ pr.commitIdFrom))、updateで値を設定する際には、タプルで渡す。

ちなみに、ググるまでもなく初めからGitBucketのリポジトリの中に答えがあったとうオチもある。当たり前だけどまずはそこのコード読むだけで自分がやりたいことは大体そこに答えがある。素敵なことです。 SlickのQueryは今回初めて読み書きしましたが、結構面白い書き方するんで、もっといろいろ遊んでみたくなりますね。

去年はScalaとか構文すらほぼ忘れてるレベル(Javaもあやうい)だったので、ここ半年ちょいいいトレーニングになったなと思い返してみる。