はじめに
Goとginで作ったHTTPサーバをHeroku上で動かすまでの試行錯誤をまとめてみました。
試行錯誤の結果、ゴールへたどり着いていますので、間違いがあると思います。
いまだに深くは理解ができていません。
参考程度にどうぞ。
最低限どういった手順で進めればよいかだけを見たい場合はまとめを見ていただければと思います。
環境
- OS: windows 10 Home
- Go: 1.13.6
- gin: 1.5.0
- Git: 2.25.0
- Text Editor: Atom
ローカル環境でのgo run main.go
はコマンドプロンプトより行います。
ginは、go get -u github.com/gin-gonic/gin
でローカル環境へ導入済みとします。
ローカル環境でのテスト
『HTML をレンダリングする』を参考にmain.goとtemplates/index.tmplを用意します。
また、フォルダ構成は以下です。
soitech-go-gin-test/
├ templates/
│ └ index.tmpl
└ main.go
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<title>{{ .title }}</title>
</head>
<body>
<h1>{{ .h1 }}</h1>
</body>
</html>
package main
import(
"net/http"
"github.com/gin-gonic/gin"
)
func main() {
router := gin.Default()
router.LoadHTMLGlob("templates/*")
router.GET("/", func(c *gin.Context) {
c.HTML(http.StatusOK, "index.tmpl", gin.H{
"title": "/",
"h1": "/",
})
})
router.GET("/hoge", func(c *gin.Context) {
c.HTML(http.StatusOK, "index.tmpl", gin.H{
"title": "hoge",
"h1": "/hoge",
})
})
router.GET("/huga", func(c *gin.Context) {
c.HTML(http.StatusOK, "index.tmpl", gin.H{
"title": "huga",
"h1": "/huga",
})
})
router.Run()
}
コマンドプロンプトよりgo run main.go
を実行し、ブラウザからlocalhost:8080
とlocalhost:8080/hoge
およびlocalhost:8080/huga
にアクセスし、プログラムが動いていることを確認します。
Herokuへデプロイする
さあ!Herokuへデプロイします!
私はGitHubへファイルをコミットしたら自動的にHeroku上でデプロイされるようにしていますので、GitHubへファイルをコミットします。
-----> App not compatible with buildpack: https://buildpack-registry.s3.amazonaws.com/buildpacks/heroku/go.tgz
More info: https://devcenter.heroku.com/articles/buildpacks#detection-failure
! Push failed
さあ、エラーが出ました!
インターネットの海で色々と調べてみると、Procfile
とvendor/vendor.json
いうものが必要らしい...
用意してみます。
web: soitech-go-gin-test
{
"rootPath": "github.com/soichiloYoda/soitech-go-gin-test"
}
コミットして、自動デプロイされると、またもやエラーです。
-----> Running: go install -v -tags heroku .
main.go:5:2: cannot find package "github.com/gin-gonic/gin" in any of:
/tmp/tmp.9lmb10Wear/.go/src/github.com/soichiloYoda/soitech-go-gin-test/vendor/github.com/gin-gonic/gin (vendor tree)
/app/tmp/cache/go1.12.12/go/src/github.com/gin-gonic/gin (from $GOROOT)
/tmp/tmp.9lmb10Wear/.go/src/github.com/gin-gonic/gin (from $GOPATH)
! Push rejected, failed to compile Go app.
! Push failed
どうやらginのimportがうまくいっていないようです。
またインターネットの海で色々調べてみると、packageの管理にはGo言語1.11より標準で使えるようになったModulesを使うようです。
こちらのページ→『Go言語の依存モジュール管理ツール Modules の使い方』を参考にさせていただきました。
プロジェクトフォルダへ移動し、vendor/
とvendor/vendor.json
を削除してgo mod init soitech-go-gin-test
をし、go.mod
を生成します。
module soitech-go-gin-test
go 1.13
その後、go build
を実行するとgo.sum
が生成され、go.mod
内に依存モジュールの情報が記述されます。
module soitech-go-gin-test
go 1.13
require github.com/gin-gonic/gin v1.5.0
GitHub上からもvendor/
とvendor/vendor.json
を削除してからgo.mod
をコミットします。
Herokuで自動デプロイされ、ようやくBuild Succeeded
となりました。
ブラウザからsoitech-go-gin-test.herokuapp.com
へ接続すると、無事HTTPサーバが動作していることが確認できました。
また、soitech-go-gin-test.herokuapp.com/hoge
とsoitech-go-gin-test.herokuapp.com/huga
へも無事接続することができました。
ちなみにですが、Procfile
を以下のように記述してデプロイしましたが、Procfile
はなくてもデプロイできるようです。
web: soitech-go-gin-test // <- おそらく間違い
また、Heroku上のBuild Log
を見るに、Procfile
は以下のように記述するのが正解なようです。
Created a Procfile with the following entries:
web: bin/soitech-go-gin-test
web: bin/soitech-go-gin-test // <- おそらく正解
Procfile
なしでデプロイすることができましたが、Heroku上のBuild Log
に以下のように表示されるため、Procfileは自分で作成しておいたほうがよさそうです。
If these entries look incomplete or incorrect please create a Procfile with the required entries.
See https://devcenter.heroku.com/articles/procfile for more details about Procfiles
まとめ
試行錯誤してみましたが最低限以下の手順を踏めばよさそうです、といったまとめです。
1.プロジェクトディレクトリを作成する
mkdir PROJECT_NAME
2.プロジェクトディレクトリ内でmodファイルを作成する
go mod init PROJECT_NAME
3.main.go
とtemplates/index.tmpl
を用意してから、一度ビルドしてmodファイルに依存モジュールの情報を記述させる。
go build
4.以下のファイルをGitHubへコミットして、Heroku上にデプロイする。
- templates/index.tmpl
- go.mod
- main.go
さいごに
とりあえず、Go言語で作成したHTTPサーバをHeroku上で動かすことができました、うれしいです。
これを元に、FormからPOSTできるものを作ってみようと思います。