作成:2023年8月8日
前回行ったPostgreSQLの練習の結果を使ってAPIを作ってみます。まずはGETから作ってみます。
今回のコードのGithub置き場です。
PostgrSQL で DB を準備
docker-compose.yaml を作成
docker-compose.yaml
# docker-composeで使用するバージョンを定義しています。
version: '3.9'
# サービス (コンテナ) を定義します。
services:
# 今回は postgres をサービスとして定義しました。
postgres:
# Docker Image は postgres:12-alpine を使います。postgres:12-alpine は postgres:12 と比較して、イメージサイズが小さくなっています。
image: postgres:12-alpine
# コンテナの名前を指定します。
container_name: postgres20230730
# 環境変数を設定します。
environment:
- POSTGRES_USER=root
- POSTGRES_PASSWORD=root
- POSTGRES_DB=testdb
# データの永続化
volumes:
# postgresボリュームを/var/lib/postgresql/dataにマウントします
- postgres20230730:/var/lib/postgresql/data
# ポートの指定(HOST:CONTAINER)
ports:
- 5432:5432
# データの永続化:ボリュームを作成します。
volumes:
postgres20230730:
コンテナ立ち上げ
コンテナを立ち上げて、PostgrSQL を確認します。
MacBook Terminal
% docker-compose up -d
% docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
af3bcf786dde postgres:12-alpine "docker-entrypoint.s…" 10 seconds ago Up 9 seconds 0.0.0.0:5432->5432/tcp, :::5432->5432/tcp postgres20230730
% docker exec -it postgres20230730 bash
af3bcf786dde:/# psql -l
List of databases
Name | Owner | Encoding | Collate | Ctype | Access privileges
-----------+-------+----------+------------+------------+-------------------
postgres | root | UTF8 | en_US.utf8 | en_US.utf8 |
template0 | root | UTF8 | en_US.utf8 | en_US.utf8 | =c/root +
| | | | | root=CTc/root
template1 | root | UTF8 | en_US.utf8 | en_US.utf8 | =c/root +
| | | | | root=CTc/root
testdb | root | UTF8 | en_US.utf8 | en_US.utf8 |
(4 rows)
PostgreSQL に接続してテーブル作成
PostgreSQL に接続します。
MacBook Terminal
af3bcf786dde:/# psql -h localhost -p 5432 -U root -d testdb
psql (12.15)
Type "help" for help.
testdb=#
テーブルを作成します。
MacBook Terminal
testdb=# create table order_list (id serial primary key, order_name varchar(255), number_of_orders integer);
CREATE TABLE
testdb=# INSERT INTO order_list VALUES (1, 'hamburger', 11);
INSERT 0 1
testdb=# INSERT INTO order_list VALUES (2, 'cheeseburger', 22);
INSERT 0 1
testdb=# INSERT INTO order_list VALUES (3, 'big_mac', 33);
INSERT 0 1
testdb=# SELECT * FROM order_list;
id | order_name | number_of_orders
----+--------------+------------------
1 | hamburger | 11
2 | cheeseburger | 22
3 | big_mac | 33
(3 rows)
Go のコード準備
main.go
package main
import (
"database/sql"
"fmt"
_ "github.com/lib/pq"
"bytes"
"encoding/json"
"log"
"net/http"
)
var DB *sql.DB
func init() {
var err error
DB, err = sql.Open("postgres", "user=root dbname=testdb password=root sslmode=disable")
if err != nil {
panic(err)
}
}
type Order struct {
Id int `json:"id"`
OrderName string `json:"order_name"`
NumberOfOrders int `json:"number_of_orders"`
}
func main() {
handler1 := func (w http.ResponseWriter, r *http.Request) {
var buf bytes.Buffer
enc := json.NewEncoder(&buf)
orders := []Order{}
rows, err := DB.Query("SELECT * FROM order_list ORDER BY id")
if err != nil {
return
}
for rows.Next() {
m := Order{}
rows.Scan(&m.Id, &m.OrderName, &m.NumberOfOrders)
fmt.Println(m)
orders = append(orders, m)
}
if err2 := enc.Encode(&orders); err2 != nil {
log.Fatal(err)
}
w.Header().Set("Access-Control-Allow-Origin","http://localhost:3000")
_, err3 := fmt.Fprint(w, buf.String())
if err3 != nil {
return
}
}
http.HandleFunc("/order", handler1)
log.Fatal(http.ListenAndServe(":8000", nil))
}
goモジュールのインストール
MacBook Terminal
% go mod init example.com/api_sql
go: creating new go.mod: module example.com/api_sql
go: to add module requirements and sums:
go mod tidy
% go mod tidy
go: finding module for package github.com/lib/pq
go: found github.com/lib/pq in github.com/lib/pq v1.10.9
実行
main.go を実行します。
MacBook Terminal
ryo@Ryo-MacBook-Pro api_sql20230730 % go run main.go
{1 hamburger 11}
{2 cheeseburger 22}
{3 big_mac 33}
別のターミナルから curl します。
MacBook Terminal
% curl http://localhost:8000/order
[{"id":1,"order_name":"hamburger","number_of_orders":11},{"id":2,"order_name":"cheeseburger","number_of_orders":22},{"id":3,"order_name":"big_mac","number_of_orders":33}]
API から GET できました。
後片付け: PostgreSQL のコンテナを落とします
MacBook Terminal
% docker-compose down
[+] Running 2/2
✔ Container postgres20230730 Removed 0.2s
✔ Network api_sql20230730_default Removed
次は、他の CRUD処理を追加していきたいと思います。
参考
Go言語の基本文法3(配列, スライス, マップ, 構造体)
【Go言語】構造体を要素に持つスライスの作成・要素追加・初期化方法まとめ
しまぶーのIT大学