読者です 読者をやめる 読者になる 読者になる

アラタナエンジニアブログ

aratana Engineer's Blog

GolangでDBデータを構造体にいい感じに突っ込む

Golang

この記事は アラタナ Advent Calendar 2016 17日目の記事です。

最近Golang(Go言語)をはじめてGopherがかわいく見えてきた中島です。
GolangでDB操作するときに、使ったライブラリが便利だったので紹介します。

Golangでは標準ライブラリのdatabase/sqlを使ってDB操作ができます。
例えば、こんな感じ(説明と関係ないところは省略してます)。

type User struct {
    ID   int    `db:"id"`
    Name string `db:"name"`
}

db, err := sql.Open("_driver", "_source")
...
defer db.Close()

rows, err := db.Query("SELECT id, name From Users")
...
defer rows.Close()
for rows.Next() {
    user := User{}
    err = rows.Scan(&user.ID, &user.Name)
    ...
}

rows.Scan(&user.ID, &user.Name) のところなんですが、カラム単位でScanするのがとてもめんどくさい。
上の例なら、カラムが2つなのでまだいいんですが、この数が増えれば増えるほどめんどくささが増していきます。

ただ、gormなどのORマッパーを使うほどではない、そんなときありますよね。もしくはORマッパーがサポートしてないDB使うときとか。

そんなときは jmoiron/sqlx が便利ですよ。
github.com

sqlxのインストール

まずはインストール方法ですが、go getでイケます。
Golangはインストール済みの前提です)

go get github.com/jmoiron/sqlx

sqlxの使い方

sqlxを使って、database/sqlで書いた上記の処理と同じものを書いてみます。

type User struct {
    ID   int    `db:"id"`
    Name string `db:"name"`
}

db, err := sqlx.Connect("_driver", "_source")
...

rows, err := db.Queryx("SELECT id, name From Users")
...
defer rows.Close()
for rows.Next() {
    user := User{}
    err = rows.StructScan(&user)
    ...
}

こんな感じです。 Queryxで取得して、StructScanで構造体に格納しています。 コードはほぼ同じですが、構造体への格納を1カラムずつやらずに済んでいることがわかるかと思います。

また、複数データまとめて構造体の配列に突っ込みたい場合は、Selectメソッドを使うと便利です。

type User struct {
    ID   int    `db:"id"`
    Name string `db:"name"`
}

db, err := sqlx.Connect("_driver", "_source")
...

users := []User{}
err := db.Select(&users, "SELECT id, name From Users")
...

だいぶスッキリしましたね。

簡単ですが、Golangのsqlxの使い方でした。
ちなみに、sqlxに加えて、 Masterminds/squirrelを組み合わせるとSQL文が書きやすくなるのでおすすめです。

次回

明日は、オブジェクト指向おじさんの木目沢さんが、たぶんオブジェクト指向の話を書いてくれます。
お楽しみに!

アラタナ Advent Calendar 2016