LoginSignup
22
7

More than 3 years have passed since last update.

Dockerでmysqlに接続できない(GO/gin/GORM)

Posted at

状況

Dockerで簡単なSPAアプリケーションの作成中にDBサーバとして作成したMySQLコンテナにバックエンドサーバ(GO/gin)がアクセスする際に

panic: dial tcp 127.0.0.1:3306: connect: connection refused

というエラーが発生する。
以下にエラーが発生したコンテナの情報とソースコードを記載し、最後に解決策を示す。

コンテナの設定

ネットワーク

$ docker network create app-nw

DBコンテナ

# コンテナを作成して起動
$ docker run --name app-db --network app-nw -p 3306:3306 -e MYSQL_ROOT_PASSWORD=root -d mysql
# 作成したMySQLコンテナに入りテーブルとレコードを作成
$ docker exec -it app-db bash
$ mysql uroot proot
mysql > create database shop;
mysql > use shop;
mysql > create table Product (
    -> ID int NOT NULL PRIMARY KEY,
    -> Name varchar(50) NOT NULL,
    -> Author varchar(50) NOT NULL
    -> );
mysql > insert into Product values (1, 'banana', 'tanaka');
# 確認用
mysql> select * from Product;
+----+--------+--------+
| ID | Name   | Author |
+----+--------+--------+
|  1 | banana | tanaka |
+----+--------+--------+
1 row in set (0.00 sec)
mysql > exit;
$ exit

バックエンドコンテナ

# コンテナを作成して起動
$ docker run --name app-webapi --network app-nw -p 8080:8080 -it ubuntu /bin/bash
# 必要なパッケージを導入
$ apt update
$ apt install -y wget
$ apt install -y git
$ wget https://golang.org/dl/go1.15.linux-amd64.tar.gz
$ tar -C /usr/local -xaf go1.15.linux-amd64.tar.gz
$ export PATH=$PATH:/usr/local/go/bin
$ go version
# インストールできていればバージョンが表示される
go version go1.15 linux/amd64
$ go get github.com/gin-gonic/gin
$ go get github.com/go-sql-driver/mysql
$ go get github.com/jinzhu/gorm

ソースコード

main.go

package main

import (
  "fmt"
  "github.com/jinzhu/gorm"
  _ "github.com/jinzhu/gorm/dialects/mysql"
)

type Product struct {
  ID int `gorm:"primary_key;not null"`
  Name string `gorm:"type:varchar(50);packanot null"`
  Author string `gorm:"type:varchar(50);packanot null"`
}

func connect() *gorm.DB {
  DBMS := "mysql"
  USER := "root"
  PASS := "root"
  PROTOCOL := "tcp(localhost:3306)"
  DBNAME := "shop"
  CONNECT := USER + ":" + PASS + "@" + PROTOCOL + "/" + DBNAME
  db, err := gorm.Open(DBMS, CONNECT)

  if err != nil {
    panic(err.Error())
  }

  db.Set("gorm:table_options", "ENGINE=InnoDB")
  db.SingularTable(true)
  db.AutoMigrate(&Product{})

  fmt.Println("db connected: ", &db)
  return db
}

func getAllProduct() [] Product {
  db := connect()
  var products []Product
  db.Find(&products)
  defer db.Close()

  return products
}

func main() {
  results := getAllProduct()
  fmt.Println(results)
}

実行結果

# /appにmain.goを作成して実行する
$ go run main.go
panic: dial tcp 127.0.0.1:3306: connect: connection refused

解決策

main.goのconnect関数を以下のように修正する。

func connect() *gorm.DB {
  DBMS := "mysql"
  USER := "root"
  PASS := "root"
  PROTOCOL := "tcp(app-db:3306)"
  DBNAME := "shop"
  CONNECT := USER + ":" + PASS + "@" + PROTOCOL + "/" + DBNAME
  db, err := gorm.Open(DBMS, CONNECT)
}

解説

dockerでgo(gin/gorm)サーバからDBコンテナを指定する場合はlocalhost127.0.0.1ではなく<コンテナ名>を指定する。
今回はコンテナ名がapp-dbなので

PROTOCOL := "tcp(app-db:3306)"

とすれば良い。

22
7
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
22
7