gcpug / nouhau

Google Cloud Platformのノウハウを共有するRepository
https://gcpug.jp
MIT License
655 stars 23 forks source link

App Engine Standard Go 1.9 migration to Go 1.11 の知見 #102

Open sinmetal opened 5 years ago

sinmetal commented 5 years ago

WHAT

App Engine Standard Go 1.9 migration to Go 1.11の知見を集約していく このissueにそのまま書いてもよいし、やった時に書いたBlogなどへのLinkでもよい

WHY

App Engine Standardにはたくさんの機能が存在していて、開発環境なども絡むと結構ややこしいので、色んな人のケースを集めてみよう。

Refs

emahiro commented 5 years ago

https://speakerdeck.com/emahiro/go-conference-2019-spring-go1-dot-9-to-go1-dot-11

ryo-yamaoka commented 5 years ago

https://techblog.ap-com.co.jp/entry/2019/04/19/174903

KeisukeYamashita commented 5 years ago

ドキュメント読んでて気づかなかったのでシェアします。

Go1.11ランタイムではAppEngineTokenSourceをつかっていると怒られました。

2019/07/01 10:45:54 google: AppEngineTokenSource is deprecated on App Engine standard second generation runtimes (>= Go 1.11) and App Engine flexible. Please use DefaultTokenSource or ComputeTokenSource.

そうしないとGCP APIが叩けません。

oauth2/google: can't get a token from the metadata service; not running on GCE
apstndb commented 5 years ago

AppEngineTokenSource が deprecated なのは事実として、 ComputeTokenSource に delegate しているはずなので動かないとしたら golang.org/x/oauth2 のバグのような気もしますね。

https://godoc.org/golang.org/x/oauth2/google#AppEngineTokenSource

Second generation App Engine runtimes (>= Go 1.11) and App Engine flexible: AppEngineTokenSource is DEPRECATED on second generation runtimes and on the flexible environment. It delegates to ComputeTokenSource, and the provided context and scopes are not used. Please use DefaultTokenSource (or ComputeTokenSource, which DefaultTokenSource will use in this case) instead.

https://github.com/golang/oauth2/blob/master/google/appengine_gen2_flex.go#L21

apstndb commented 5 years ago

2018年11月時点で動くようには書かれているはずなので、動かなかった条件が少し知りたいところですね。 aetest とか dev_appserver.py で動かないのは間違いないと思います。 https://github.com/golang/oauth2/pull/341

KeisukeYamashita commented 5 years ago

oauth2/google: can't get a token from the metadata service; not running on GCE

これはAppEngineTokenSourceにしていたときにエラーが出たもので、DefaultTokenSourceにするとすんなり解決したためComputeTokenSourceは試していません。

2019/07/01 10:45:54 google: AppEngineTokenSource is deprecated on App Engine standard second generation runtimes (>= Go 1.11)

ここはGo1.11はsecond generation runtimes扱いなんだとびっくりしましたw

apstndb commented 5 years ago

試しに google.AppEngineTokenSource を使ったものを App Engine Go 1.11 にデプロイしてみたところAppEngineTokenSource is deprecated のログは出力されたものの動いたので、動かないというのはやはり何か前提条件がおかしい気がしますね。

oauth2/google: can't get a token from the metadata service; not running on GCE

が出ているということは、デプロイ先がおかしい OR デプロイしないローカル環境での結果ではないでしょうか。 下は実際に動かしてみたもの。

```go:main.go package main import ( "fmt" "io" "net/http" "os" "golang.org/x/oauth2" "golang.org/x/oauth2/google" "google.golang.org/appengine" ) func main() { http.HandleFunc("/", func(rw http.ResponseWriter, r *http.Request) { tokenSource := google.AppEngineTokenSource(r.Context()) client := oauth2.NewClient(r.Context(), tokenSource) resp, err := client.Get(fmt.Sprintf(`https://appengine.googleapis.com/v1/apps/%s/services`, os.Getenv("GOOGLE_CLOUD_PROJECT"))) if err != nil { http.Error(rw, err.Error(), http.StatusInternalServerError) return } defer resp.Body.Close() io.Copy(rw, resp.Body) }) appengine.Main() } ``` ```yaml:app.yaml runtime: go111 service: go111-tokensource ```
nanasi880 commented 5 years ago

移行時にはまったことや解決策, ワークアラウンド

ような場合、そのままgcloud app deployしてしまうとGAEのapp_builderさんがCloudBuildマシンから認証が必要なGitHubリポジトリにアクセスしようとしてビルド出来ないので、デプロイ前に小細工が必要でした

具体的には

go mod vendor
mv ./go.mod ./go.mod.temp
mv ./go.sum ./go.sum.temp
gcloud app deploy

のように、vendorフォルダを作った後、go.modファイルをリネームするなり何なりしてやる必要があります go111ランタイムの初期の頃はgcloud app deployする際に環境変数GO111MODULEが参照されているような挙動だったのですが、いつからかgo.modファイルがあるかどうかでGo Moduleを使うかどうかが変わるようになりました

apstndb commented 5 years ago

実は go mod vendor については Cloud Functions のドキュメントの方が詳しくて、 go.mod を無視するために .gcloudignore が使えることも書いてあったりしますね。こちらに挙動が合わせられている様子。 https://cloud.google.com/functions/docs/writing/specifying-dependencies-go?hl=en#using_a_vendor_directory

sinmetal commented 5 years ago

https://github.com/gcpug/nouhau/tree/master/app-engine/note/gaego111-private-repo-deploy も合わせてどうぞ!

nanasi880 commented 5 years ago

誘導ありがとうございます 今は.gcloudignoreでちゃんと間引けるようになってるんですね :)

hogedigo commented 5 years ago

dev_appserver.pyにbug。

handlers:

- url: /hello
  script: auto

- url: /(.+)
  static_files: static/\1
  upload: static/.*

上記の様に scriptハンドラを上書きするURLパターンのstatic_filesハンドラがあると、scriptハンドラが処理されず404エラーとなる。 (dev_appserverはgo1.11の場合にscriptハンドラを全て無視してデフォルトハンドラで処理している為)

プロダクションでは問題なし。

↓issue https://issuetracker.google.com/issues/128170900