この章では、Golang MongoDBドキュメントクエリの使用方法について紹介します。

前提チュートリアル

ヒント:MongoDBクエリ構文に馴染みがない場合は、まずMongoDBチュートリアルを読んでください。GolangでのMongoDB操作に使用する式構文は同じです。

テストデータの準備

coll コレクションに複数のドキュメントデータを挿入します。

docs := []interface{}{
    bson.D{
        {"item", "journal"},
        {"qty", 25},
        {"size", bson.D{
            {"h", 14},
            {"w", 21},
            {"uom", "cm"},
        }},
        {"status", "A"},
    },
    // ... (他のドキュメントデータ)
}

result, err := coll.InsertMany(context.Background(), docs)

すべてのドキュメントをクエリする

cursor, err := coll.Find(
    context.Background(),
    bson.D{}, // 空のクエリ条件を設定
)

等しいクエリ条件

SQLの等しいマッチと同様です。

cursor, err := coll.Find(
    context.Background(),
    bson.D{{"status", "D"}},   // 同等の条件:status = D
)

in クエリ演算子

SQLの in クエリに類似しています。

cursor, err := coll.Find(
    context.Background(),
    bson.D{{"status", bson.D{{"$in", bson.A{"A", "D"}}}}}) // 同等の条件:status in ('A', 'D')

and クエリ条件

SQLの and 論理式に類似しています。

cursor, err := coll.Find(
    context.Background(),
    bson.D{ // 同等の条件:status='A' かつ qty < 30 
        {"status", "A"},
        {"qty", bson.D{{"$lt", 30}}},
    })

or クエリ条件

SQLの or 論理式に類似しています。

cursor, err := coll.Find(
    context.Background(),
    bson.D{ // 同等の条件:status = "A" または qty < 30
        {"$or", // $or演算子を使用
            bson.A{ // bson.A配列型の定義を使用
                bson.D{{"status", "A"}},
                bson.D{{"qty", bson.D{{"$lt", 30}}}},
            }},
        },
    })

複合クエリの例

cursor, err := coll.Find(
    context.Background(),
    bson.D{ // 同等の条件:status = "A" かつ ( qty < 30 または item が "p%" で始まる)
        {"status", "A"},
        {"$or", bson.A{
            bson.D{{"qty", bson.D{{"$lt", 30}}}},
            bson.D{{"item", primitive.Regex{Pattern: "^p", Options: ""}}},
        }},
    })

クエリ結果のトラバース

例1

// name が 'Bob' のドキュメントをクエリ
cursor, err := coll.Find(context.TODO(), bson.D{{"name", "Bob"}}, opts)
if err != nil {
	log.Fatal(err)
}

// bson.M型のドキュメントの配列を定義し、bson.Mはマップに似たキーと値のデータ構造です。
var results []bson.M
// All 関数を使用してすべてのクエリ結果を取得し、その結果を results 変数に保存します。
if err = cursor.All(context.TODO(), &results); err != nil {
	log.Fatal(err)
}

// results 配列をトラバースします
for _, result := range results {
	fmt.Println(result)
}

説明:この例では、bson.M型を使用してドキュメントデータを保存しています。フィールドがドキュメントと一致する限り、構造体型をカスタマイズできます。

例2:

// クエリ結果を保存するための構造体型の変数を定義します
var result struct {
    Value float64
}

// name = 'pi' のドキュメントクエリ条件を定義します
filter := bson.D{{"name", "pi"}}
// コンテキストオブジェクトを作成し、クエリのタイムアウトを5秒に設定します
ctx, cancel = context.WithTimeout(context.Background(), 5*time.Second)
defer cancel()

// 条件に基づいて単一のデータをクエリし、Decode 関数を使用して結果を result 変数に保存します。
err = collection.FindOne(ctx, filter).Decode(&result)

// クエリエラーをチェックします
if err == mongo.ErrNoDocuments {
    // ドキュメントが見つかりません
    fmt.Println("ドキュメントは存在しません")
} else if err != nil {
    log.Fatal(err)
}
// その他の処理

ヒント:より高度なMongoDBクエリ式構文については、MongoDBチュートリアルを参照してください。