Zenn
💻

Go言語環境構築DB接続DB操作/おまけHelloWorld

2025/03/22に公開

前提
https://a.r10.to/hPLPuw
書籍を元に少し値や名を変えて手を動かしております。
入門者のためコメントアウトをして定着させるための記事化でありコメントアウトが多々。未経験Goに触れてみたい方の参考になればと思う反面2次情報のため鵜吞みにせず公式ドキュメントを基準に参考頂けますと幸いです。

環境構築
・SQLlite
https://www.sqlite.org/download.html
sqlite-dll-win-x64-3490100.zip

・コンパイルツールgcc
https://jmeubank.github.io/tdm-gcc/download/
stdm64-gcc-10.3.0-2.exe

bash
gcc --version

・Go install
https://go.dev/
go version

・Git (Win) install
https://git-scm.com/

・VSCode (Win) install
拡張:「Jpanese Languge Pack for」「Go」

go.mod 作成
 go mod init awesomeProject
 go get github.com/mattn/go-sqlite3
Hello.go
package main

import "fmt"

func main() {
	fmt.Println("HelloWorld")
}
bash
 go run Hello.go
//HelloWorld

・DB接続

lesson.go
package main

import (
	"database/sql"
	"log"

	_ "github.com/mattn/go-sqlite3"
)

var DbGate *sql.DB //sql.db の変数宣言。 database/sql パッケージにある DB 型を指す。

func main() {
	DbGate, _ := sql.Open("sqlite3", "./example.sql") //sql.Open関数でDB開く。 _ はブランク識別子sql.Open のエラー戻り値を無視
	defer DbGate.Close()                              //defer文ファイル閉じ忘れ防止(処理を遅らせて実行)。Closeメソッド
	//CREATE作成
	cmd := `CREATE TABLE IF NOT EXISTS budget(
	name STRING,
	age INT
	)`

	_, err := DbGate.Exec(cmd) //Execメソッド データベース操作 引数cmd はSQLコマンド「命令そのもの」
	if err != nil {
		log.Fatalln(err)
	}
  //INSERT
	cmd = "INSERT INTO budget (name,age) VALUES (?,?)" //レコードの追加
	_, err = DbGate.Exec(cmd, "MIYA", 20)

	if err != nil {
		log.Fatalln(err) //重大なエラーを出力して即終了
	}
}
bash
go run lesson.go
#実行後example.sqlファイルが作成される

SELECT文で現在の値を取得確認

bash
sqlite3 example.sql
sqlite> select * from budget;
MIYA|20
.exit
lesson.go
_, err = DbGate.Exec(cmd, "cat", 10)               //MIYA 20を書き換えてレコード追加
bash
sqlite3 example.sql
sqlite> select * from budget;
MIYA|20
cat|10
.exit
lesson.go
//UPDAATE文
cmd = "UPDATE budget SET age = ? WHERE name =?"
_, err = DbGate.Exec(cmd, 21, "MIYA") //age 20→21にレコード更新

if err != nil {
log.Fatalln(err)
}

再実行

bash
sqlite> select * from budget;
MIYA|21
cat|10
cat|10
sqlite>
lesson.go
package main

import (
	"database/sql"

	"log"

	_ "github.com/mattn/go-sqlite3"
)

var DbGate *sql.DB //sql.db の変数宣言。 database/sql パッケージにある DB 型を指す。

func main() {
	DbGate, _ := sql.Open("sqlite3", "./example.sql") //sql.Open関数でDB開く。 _ はブランク識別子sql.Open のエラー戻り値を無視
	defer DbGate.Close()                              //defer文ファイル閉じ忘れ防止(処理を遅らせて実行)。Closeメソッド
	//CREATE作成
	cmd := `CREATE TABLE IF NOT EXISTS budget(
	name STRING,
	age INT
	)`

	_, err := DbGate.Exec(cmd) //Execメソッド データベース操作 引数cmd はSQLコマンド「命令そのもの」
	if err != nil {
		log.Fatalln(err)
	}

	cmd = "INSERT INTO budget (name,age) VALUES (?,?)" //レコードの追加
	_, err = DbGate.Exec(cmd, "cat", 10)               //MIYA 20を書き換えてレコード追加

	if err != nil {
		log.Fatalln(err) //重大なエラーを出力して即終了
	}

	//UPDAATE文
	cmd = "UPDATE budget SET age = ? WHERE name =?"
	_, err = DbGate.Exec(cmd, 21, "MIYA") //age 20→21

	if err != nil {
		log.Fatalln(err)
	}

  //DELETE文でレコードを削除
	cmd = "DELETE FROM budget WHERE name = ?"
	_, err = DbGate.Exec(cmd, "cat")
	if err != nil {
		log.Fatalln(err)
	}

}

SELECT文で1件取得 QueryRowメソッド
構造体を大文字で作成(他のパッケージからアクセス可能)

lesson.go
package main

import (
	"database/sql"
	"fmt"
	"log"

	_ "github.com/mattn/go-sqlite3"
)

var DbGate *sql.DB //sql.db の変数宣言。 database/sql パッケージにある DB 型を指す。

	//構造体の定義BudgetBudget
	type Budget struct {
		Name string
		Age  int
	}

func main() {
	DbGate, _ := sql.Open("sqlite3", "./example.sql") //sql.Open関数でDB開く。 _ はブランク識別子sql.Open のエラー戻り値を無視
	defer DbGate.Close()                              //defer文ファイル閉じ忘れ防止(処理を遅らせて実行)。Closeメソッド
	//CREATE作成
	cmd := `CREATE TABLE IF NOT EXISTS budget(
	name STRING,
	age INT
	)`

	_, err := DbGate.Exec(cmd) //Execメソッド データベース操作 引数cmd はSQLコマンド「命令そのもの」
	if err != nil {
		log.Fatalln(err)
	}


	//SELECT文で1件レコードを取得 QueryRowメソッド
	cmd = "SELECT * FROM budget WHERE age = ?"
	row := DbGate.QueryRow(cmd, 21)
	var p Budget
	err = row.Scan(&p.Name, &p.Age)

	if err != nil {
		if err == sql.ErrNoRows {
			log.Println("No row")
		} else {
			log.Println(err)
		}
	}
	fmt.Println(p.Name, p.Age)
bash
go run lesson.go   
MIYA 21

全取得の場合の解説Queryメソッド

lesson.go
package main

import (
	"database/sql"
	"fmt"
	"log"

	_ "github.com/mattn/go-sqlite3"
)

var DbGate *sql.DB //sql.db の変数宣言。 database/sql パッケージにある DB 型を指す。

type budget struct {
	Name string
	Age  int
}

func main() {
	DbGate, _ := sql.Open("sqlite3", "./example.sql") //sql.Open関数でDB開く。 _ はブランク識別子sql.Open のエラー戻り値を無視
	defer DbGate.Close()                              //defer文ファイル閉じ忘れ防止(処理を遅らせて実行)。Closeメソッド
	//CREATE作成
	cmd := `CREATE TABLE IF NOT EXISTS budget(
	name STRING,
	age INT
	)`

	_, err := DbGate.Exec(cmd) //Execメソッド データベース操作 引数cmd はSQLコマンド「命令そのもの」
	if err != nil {
		log.Fatalln(err)
	}

	//Queryメソッドで全レコード取得

	// データベースから全データを取得
	cmd = "SELECT * FROM budget" // "budget"表の全部を取る命令を準備

	rows, _ := DbGate.Query(cmd) // 命令を実行して結果をrowsに保存(エラーは無視)

	defer rows.Close() // 使い終わったらrowsを閉じる予約

	var pp []budget // データを集める空のリストを作る

	for rows.Next() { // 1行ずつ見ていく
		var p budget                      // 1行分のデータを入れる箱
		err := rows.Scan(&p.Name, &p.Age) // データをpにコピー
		if err != nil {
			log.Println(err) // エラーがあれば記録
		}
		pp = append(pp, p) // pをリストに追加
	}

	for _, p := range pp { // リストの中身を全部表示
		fmt.Println(p.Name, p.Age) // 名前と年齢を画面に出す
	}
}

Queryメソッドで全レコード取得 まとめ

rows.Next() で表のデータを1行ずつ見る。
p に1行分のデータ(例: 太郎, 13)を入れる。
pp = append(pp, p) で、そのデータをスライス(pp)に追加。
全部集めたら、pp を使って表示。

別途おまけHelloWorld

Hello.go ※以降DB接続には触れておりません。
package main
import "fmt"
func main() {
fmt.Println("HelloWorld")
 }

net/http利用「localhost:8080」webサーバー立ち上げ

Hello.go ※HelloWorldの書き換え
package main

import (
	"log"
	"net/http"
)

func viewHandler(w http.ResponseWriter, r *http.Request) {
	// レスポンスとして簡単なメッセージを返す
	_, err := w.Write([]byte("Hi、直接的な書き込みのviewです"))
	if err != nil {
		log.Println("レスポンスの書き込み時エラー:", err)
	}
}

func main() {
	http.HandleFunc("/view/", viewHandler) //http.HandleFunc。viewHandler関数
	log.Fatal(http.ListenAndServe(":8080", nil))
}

//http://localhost:8080
//http://localhost:8080/view/test

Discussion

ログインするとコメントできます