Posts for: #Postgresql

sql の group concat という組み込み関数

2時に寝て7時に起きた。昨日の hannali dao が盛り上がった影響で夜更ししてた。

本番リリース後の緊急対応

昨日あるバッチ処理の本番リリースを行った。そのバッチ処理は本番環境のデータがないとテスト環境ではあまり有効な検証ができない。昨日は別のバグがあって実行できていなかったのを今日直して再実行したらまた別のバグを発見した。sql である集合を取得するときのグルーピングの条件が適切ではなかった。postgresql で mysql でいうところの group_concat に相当することをやりたい。How to Use string_agg() のチュートリアルをちょっとカスタマイズして引用する。次のようなデータがあると仮定する。

> select * from teams ;
  team_name  | team_member | num
-------------+-------------+-----
 Barcelona   | Messi       |   1
 Barcelona   | Piquet      |   2
 Barcelona   | (null)      |   3
 Real Madrid | Ronaldo     |   1
 Real Madrid | Benzema     |   2
 Real Madrid | Ramos       |   3
(6 )

このときに team_name に対して team_member も集約して数値の合計を取りたいときがある。string_agg という組み込み関数を使うとできる。null があっても無視して数値の合計はしてくれる。

> select team_name, string_agg(team_member, ','), sum(num) from teams group by team_name;
  team_name  |      string_agg       | sum
-------------+-----------------------+-----
 Real Madrid | Ronaldo,Benzema,Ramos |   6
 Barcelona   | Messi,Piquet          |   6
(2 )

送別会

プロジェクトの区切りの打ち上げと、私が今週末で契約終了となるので送別会を兼ねて催してくれた。感謝。実はこれまでプロジェクトの打ち上げに私は参加してこなかった。それは複数の意図があった。オンライン飲み会だと人数が多いほど話しにくいし、若い人たちだけの方が年長者に配慮しなくてたくさん話せていいんじゃないかと考えていた。私のような老い先短いメンバーがチームに馴染んでなくても日々の業務に変わりはないし、業務で発言しにくいといったこともないし、他に山ほど仕事の積み上げがあって他のことに時間を使えるならそれに越したこともない。過去に2-3回打ち上げしていたと思うけど、私は今回が最初で最後の参加となった。

都合のある人はばらばら抜けたりもしていたけど、9人ほどずっと参加していて20時から始めて23時過ぎまでやっていた。この人数だと、みんなが話せるというわけでもなくて、本当に2つのグループに分けて雑談した方がよかったのかもしれない。私は1-2割ぐらいの時間を話していたと思うけど、ほとんど聞いているだけで話さないメンバーも半分ぐらいはいたと思う。それは年長者がたくさん話せるように配慮して若い人たちが話しにくいというのは実際にあるのではないかなとも思えた。終わりの時間を決めておかないと延々話しが続いてしまう。チキンレースみたいになってしまって誰かが抜けると言わないと終わらない雰囲気になってしまった。それが23時過ぎで、ある人がそろそろ抜けますと宣言して「私も」「僕も」と続いて、じゃあお開きにしましょみたいなノリで解散となった。いろいろな話しができて楽しかった。

postgresql の json データ型

1時に寝て6時半に起きた。連休中に夜更ししてたから生活が乱れた。

ロガー向けのログ保存 API の開発

先週の休暇前にやっていた作業の開発に着手。一通り web api のエンドポイントの実装は終えてテストをあらかた書いたところ。いまのプロジェクトとしても、過去の私の経験としてもやったことのない新しい挑戦の1つとして postgresql の JSONデータ型 を使う。具体的には json 型と jsonb 型の2つがある。前者はテキストで保持する型で、後者は内部的にバイナリに変換されてインデックスも使える。バイナリに変換してインデックスを作る分、insert 時にテキストで保存するよりは少し余分なオーバーヘッドを要する。json のデータを参照用途で使うのか、検索するのかでこれらの型を使い分ければいいのかな。

実際の sql で json データの条件指定は次のようになる。@> というみたこともない気持ち悪い演算子を使う。

> select * from mytable where data  @> '{"x": 1, "y": 2}';

java の jdbc で扱うには PGobject という型に変換して扱う必要がある。

private PGobject convertData(String value) throws SQLException {
    var data = new PGobject();
    data.setType("jsonb");
    data.setValue(value);
    return data;
}

余談だけど、curl で json 文字列を query string としてリクエストするには url encode しないといけない。

$ curl -s --get --data-urlencode 'data={"x": 1, "y": 2}' http://localhost/path | jq .