Carpe Diem

備忘録

gRPCで大きなファイルのやり取りをする

概要

gRPCで4MB以上のデータ転送をしようとすると

rpc error: code = ResourceExhausted desc = grpc: received message larger than max (xxxxxxx vs. 4194304)

のようなエラーが出ます。この上限はデフォルト値なのでgrpc.MaxRecvMsgSize()grpc.MaxCallSendMsgSize()を使うことで変更可能ですが、ドキュメントでも以下のように

Protocol Buffers are not designed to handle large messages. As a general rule of thumb, if you are dealing in messages larger than a megabyte each, it may be time to consider an alternate strategy.

ref: Techniques  |  Protocol Buffers  |  Google Developers

と、1メッセージがメガバイトを超えるのであれば別の手段で転送することを考えるべき、と言っています。

なので

のようにストリームで送るのが良さそうです。

続きを読む

Circusを使ってgraceful restart

概要

Nginx + GoのApp

という構成をとっている時に、単純にデプロイでGoだけ更新するとNginxからは

[error] 1413#1413: *1 connect() failed (111: Connection refused)
[error] 1412#1412: *3 connect() failed (111: Connection refused)
[error] 1412#1412: *5 connect() failed (111: Connection refused)

このような111: Connection refusedエラーが起きて、クライアント側には502エラーが返ってしまいます。
理由はデプロイ時にプロセスが一時的に落ちるためです。

これを防ぐためにCircusというソケットマネージャを利用します。

環境

  • Ubuntu 16.04
  • Nginx 1.15.3
  • Circus 0.15.0
  • go 1.11.5
続きを読む

.proto ファイルの整形に clang-format を使う

概要

gRPCで通信しようとすると.protoファイルが沢山出てきます。
ただ人によってインデントが異なったりするのは良くないので、何かしらformatterが無いかなと探したら

github.com

こちらのissueで「Googleではclang-formatを使ってるよ」という回答があったのでそれを使ってみます。

環境

  • macOS Mojave 10.14.2
  • clang-format 8.0.0
続きを読む

VPN接続するとどうして別ネットワークにアクセスできるのか

概要

VPNサーバをAWSに置くことで内部ネットワークに外部からアクセスする手法がありますが、どうしてそれができるのかを知りたくなって調べてみました。

環境

VPNサーバ

  • Ubuntu v18.04
  • pritunl v1.29.1958.76

クライアント

ネットワーク環境

イメージは以下の図です。

f:id:quoll00:20190125234530p:plain

続きを読む

CircleCI 2.1 でconfigの記述をシンプルにする

概要

christina04.hatenablog.com

でCircleCIの使い方を説明しましたが、2.1からconfigの記述がよりシンプルになりましたので説明します。

環境

  • CircleCI 2.1

設定

CircleCI側

まずはAdvanced Settingsで2.1の機能が使えるようにします。

f:id:quoll00:20190125133015p:plain

古いプロジェクトだとOFFのままなのでONにしてください。新しいプロジェクトだと最初からONになっています。

続きを読む

goroutineでのpanicのハンドリング その2

概要

christina04.hatenablog.com

で書いていなかったことの追加です。

環境

recoverしたあとのエラーハンドリングをどうするか

panicをrecoverしたものはいいものの、

func f() {
    defer func() {
        if r := recover(); r != nil {
            fmt.Println("Recovered in f", r)
        }
    }()

    panic("panic")
}

The Go Playground

このように単純にrecoverしてハイ終わり、としているとpanicを起こしたのに処理が正常系で進んでしまうという問題があります。

特にWebサーバとしてはpanicが起きたので500エラーとして返すべきです。
なのでpanicをerrorに変換して、後の処理にerrorを渡す必要があります。

続きを読む

ConsulでService登録をした時のACLでハマった話

概要

Consulではserviceを登録することでService Discovery機能を活用することができます。
例えば

  "service": {
    "name": "payment",
    "port": 9090,
    "tags": ["development"]
  }

のように設定をすると、

$ dig @localhost -p 8600 payment.service.consul

paymentサービスとして登録したノードのIP群を取得できます。
詳細を知りたい方は以下を参考にしてください。

christina04.hatenablog.com

今回はこのサービス登録でACLを設定しているとうまく行かずハマってしまった話です。

続きを読む