Go (Golang) は、堅牢で高性能のバックエンド サービスを構築するための一般的な選択肢となっています。 Go の主な強みの 1 つは、従来の SQL データベースを使用しているか最新の NoSQL ソリューションを使用しているかにかかわらず、データベース操作に対する優れたサポートです。このガイドでは、SQL と NoSQL の両方のアプローチをカバーしながら、Go でデータベースを操作する方法を説明します。
Go の標準ライブラリは、SQL (または SQL に似た) データベースに関する汎用インターフェイスを提供する、database/sql パッケージを提供します。このパッケージは、データベース固有のドライバーと組み合わせて使用するように設計されています。
SQLite を使用した簡単な例から始めましょう:
package main import ( "database/sql" "fmt" "log" ) func main() { // Open the database db, err := sql.Open("sqlite3", "./test.db") if err != nil { log.Fatal(err) } defer db.Close() // Create table _, err = db.Exec(`CREATE TABLE IF NOT EXISTS users ( id INTEGER PRIMARY KEY AUTOINCREMENT, name TEXT, age INTEGER )`) if err != nil { log.Fatal(err) } // Insert a user result, err := db.Exec("INSERT INTO users (name, age) VALUES (?, ?)", "Alice", 30) if err != nil { log.Fatal(err) } // Get the ID of the inserted user id, err := result.LastInsertId() if err != nil { log.Fatal(err) } fmt.Printf("Inserted user with ID: %d\n", id) // Query for the user var name string var age int err = db.QueryRow("SELECT name, age FROM users WHERE id = ?", id).Scan(&name, &age) if err != nil { log.Fatal(err) } fmt.Printf("User: %s, Age: %d\n", name, age) }
この例では、Go での SQL データベースの操作の基本を示します。
database/sql パッケージはデータベースへの低レベルのインターフェイスを提供し、クエリと操作を細かく制御できます。
database/sql パッケージは強力ですが、多くの開発者は、より便利なデータベース操作のためにオブジェクト リレーショナル マッピング (ORM) ツールの使用を好みます。 GORM は Go で最も人気のある ORM の 1 つです。
SQLite で GORM を使用する例を次に示します:
package main import ( "fmt" "log" "gorm.io/driver/sqlite" "gorm.io/gorm" ) type User struct { ID uint Name string Age int } func main() { // Open the database db, err := gorm.Open(sqlite.Open("test.db"), &gorm.Config{}) if err != nil { log.Fatal(err) } // Auto Migrate the schema db.AutoMigrate(&User{}) // Create a user user := User{Name: "Bob", Age: 25} result := db.Create(&user) if result.Error != nil { log.Fatal(result.Error) } fmt.Printf("Inserted user with ID: %d\n", user.ID) // Query for the user var fetchedUser User db.First(&fetchedUser, user.ID) fmt.Printf("User: %s, Age: %d\n", fetchedUser.Name, fetchedUser.Age) // Update the user db.Model(&fetchedUser).Update("Age", 26) // Delete the user db.Delete(&fetchedUser) }
GORM はデータベース操作に対するより高いレベルの抽象化を提供し、生の SQL クエリを記述する代わりに Go 構造体を直接操作できるようにします。また、自動移行、フック、関連付けなどの機能も提供します。
NoSQL データベースの場合、公式 Go ドライバーを使用して MongoDB と対話する方法を見てみましょう。
package main import ( "context" "fmt" "log" "time" "go.mongodb.org/mongo-driver/bson" "go.mongodb.org/mongo-driver/mongo" "go.mongodb.org/mongo-driver/mongo/options" ) type User struct { Name string `bson:"name"` Age int `bson:"age"` } func main() { // Set client options clientOptions := options.Client().ApplyURI("mongodb://localhost:27017") // Connect to MongoDB ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second) defer cancel() client, err := mongo.Connect(ctx, clientOptions) if err != nil { log.Fatal(err) } // Check the connection err = client.Ping(context.TODO(), nil) if err != nil { log.Fatal(err) } fmt.Println("Connected to MongoDB!") // Get a handle for your collection collection := client.Database("test").Collection("users") // Insert a user user := User{Name: "Charlie", Age: 35} insertResult, err := collection.InsertOne(context.TODO(), user) if err != nil { log.Fatal(err) } fmt.Printf("Inserted user with ID: %v\n", insertResult.InsertedID) // Find a user var result User filter := bson.M{"name": "Charlie"} err = collection.FindOne(context.TODO(), filter).Decode(&result) if err != nil { log.Fatal(err) } fmt.Printf("Found user: %+v\n", result) // Update a user update := bson.M{ "$set": bson.M{ "age": 36, }, } updateResult, err := collection.UpdateOne(context.TODO(), filter, update) if err != nil { log.Fatal(err) } fmt.Printf("Updated %v user(s)\n", updateResult.ModifiedCount) // Delete a user deleteResult, err := collection.DeleteOne(context.TODO(), filter) if err != nil { log.Fatal(err) } fmt.Printf("Deleted %v user(s)\n", deleteResult.DeletedCount) // Disconnect err = client.Disconnect(context.TODO()) if err != nil { log.Fatal(err) } fmt.Println("Connection to MongoDB closed.") }
この例では、公式 Go ドライバーを使用した MongoDB での基本的な CRUD (作成、読み取り、更新、削除) 操作を示します。
Go でデータベースを操作する場合は、次のベスト プラクティスに留意してください。
接続プーリングを使用する: データベース/SQL ドライバーとほとんどの NoSQL ドライバーの両方が接続プーリングを実装します。操作ごとに新しいデータベース接続を開くのではなく、必ずデータベース接続を再利用してください。
エラーを適切に処理する: データベース操作によって返されたエラーを常に確認し、適切に処理します。
プリペアド ステートメントを使用する: SQL データベースの場合、プリペアド ステートメントを使用してパフォーマンスを向上させ、SQL インジェクション攻撃を防ぎます。
リソースを閉じる: 結果セット、ステートメント、データベース接続を使い終わったら、必ず閉じてください。これには defer キーワードが役立ちます。
必要に応じてトランザクションを使用する: 複数の手順が必要な操作の場合は、トランザクションを使用してデータの一貫性を確保します。
N 1 クエリの問題に注意してください: ORM を使用するときは、N 1 クエリの問題に注意し、必要に応じて積極的な読み込みを使用してください。
タイムアウトにコンテキストを使用する: コンテキストを使用して、データベース操作、特に長時間実行クエリのタイムアウトを設定します。
避けるべき一般的な落とし穴:
Go は、SQL と NoSQL の両方のデータベース対話に対する強力なサポートを提供します。データベース/SQL の低レベル制御を好む場合でも、GORM などの ORM の利便性を好む場合でも、MongoDB などの NoSQL データベースでの作業を好む場合でも、Go はそれを実現します。
以上がGo でのデータベース インタラクション: SQL から NoSQL への詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。