Carpe Diem

備忘録

Go

CPU CFS Quotaを制限している場合の適切なGOMAXPROCS

概要 christina04.hatenablog.com 以前上の記事でGOMAXPROCSはCPU数程度が適切に動くという話をしました。 これはこれで正しいのですが、一方でdockerのようにcgroupsでCPU Quotaを制限するケースではこれに当てはまらなくなります。 Kubernetesでいうと Kub…

Go Module MirrorとChecksum Database

Go

概要 Go 1.13から、goコマンドはデフォルトでGo Module MirrorとChecksum Databaseを使用してモジュールをダウンロード&認証するようになりました。 環境 go 1.14.1 Module Mirror (Module Proxy) Module Mirrorは公開モジュールをキャッシュし、go modでの…

go generateでモックを生成する

Go

背景 Clean Architecture に則ってレイヤ間をプラガブルにするためにインタフェースを使っていくと、テストのために各インタフェースのモックが欲しくなります。 そのモックを生成する際にgolang/mockを使用するわけですが、毎回 $ mockgen -source user.go …

gRPCでのLoad Balancing

背景 gRPCでは主に Proxy Model Balancing-aware Client External Load Balancing Service といったLBアプローチがあります。 それぞれの特徴や実装方法を調べてみました。 Load Balancingアプローチ こちらで定義されてます。 grpc/load-balancing.md at ma…

gRPCでのClient-Side LB実装の変遷

概要 gRPCでのバランシングをClient-Sideで直接実装する方法の紹介です。 gRPCはPolyglot(様々な言語で扱う)を意識しているので、gRPC自体の仕様が策定→各言語がそれに則って実装となります。 なので「元々はこういう実装だったけど、他の言語と統一してこ…

go modulesでコマンドラインツールのバージョン管理をする

Go

概要 goはModulesでリポジトリのライブラリのバージョン管理を行えます。 ただコマンドラインツールに関してはgo getしてgo.modに追加されても、goファイルで扱っているわけではないのでgo mod tidyすると消えてしまいます。 しかしながら「この機能は最新の…

GoのDIツールwireで知っておくと良いこと

Go DI

概要 christina04.hatenablog.com こういった設計のようにレイヤ間の依存関係を抽象化していると、DIの初期化処理が段々冗長になっていきます。 google/wireはそういったDIの初期化を自動的にやってくれるコード生成ツールです。 今回はwireを使う上で知って…

vim-goからvim-lspへ移行しました

概要 vim-goからvim-lspへ移行する時に問題になってたところを全部mattnさんが解決してくださってたのでようやく完全移行したという話です。 環境 vim 8.2 go 1.13.5 これまでの課題 vim-goの問題点 2014年からgoを触っていましたが当時はvim-go一択で、しか…

cgoを使わないGoのクロスコンパイル時に -installsuffix cgo が不要になってた

概要 以前Docker multi stage buildなどビルド環境と実行環境が異なる(クロスコンパイル)時に、単純にGOOSやGOARCHをセットするだけではなく $ CGO_ENABLED=0 GOOS=linux GOARCH=amd64 \ go build -a -installsuffix cgo -o main main.go のように CGO_ENA…

Go の http.Server は各種 Timeout をセットした方が良い

Go

概要 以前↓の記事を紹介しましたが、 christina04.hatenablog.com http.Serverの各Timeoutを使わないと TCPハンドシェイクをしたあと全くリクエストを送ってこないクライアント Slowloris DDoS attack による大量接続攻撃を受けた時に困るので注意してくださ…

pipeエラーのハンドリング

概要 write: broken pipeといったクライアント側の強制的なコネクション切断でのエラーハンドリングをする際の知見まとめ。 環境 go 1.13.3 事前知識 知っておくと良い知識を先に説明します。 そもそもpipeとは pipeはプロセス間通信をするための単方向のデ…

Goのnet/httpのkeep-aliveで気をつけること

概要 Idle connectionをプールするkeep-aliveの仕組みですが、golangで適切に使用するためにはいくつか注意があります。 環境 golang 1.13.1 TCP Keep-Aliveの挙動をパケットキャプチャで確認する 例えば以下のようにDefaultTransportの一部の設定(①、②)を…

Goのnet/httpのtimeoutについて

Go

概要 タイムアウトと一口に言ってもサーバ・クライアント、そして各フェーズによって細かく設定があります。 今回はGoのnet/httpのtimeoutについて1つ1つ説明していきます。 環境 golang 1.13 Server 全体図 サーバ系timeoutと各フェーズは以下の関係にな…

gRPC Unary Interceptorを複数設定した時の実行順序

概要 以前 christina04.hatenablog.com にてgRPCのUnary Interceptorの基本的な使い方を説明しました。 このInterceptorを複数設定したい時に使われるのがgo-grpc-middlewareの出している ChainUnaryServer ChainUnaryClient です。READMEにありますが、以下…

Go言語でプラグイン機構【RPC編】

概要 オブジェクト指向についてClean Architectureでは OOとは「ポリモーフィズムを使用することで、システムにあるすべてのソースコードの依存関係を絶対的に制御する能力」である。 これにより、アーキテクトは「プラグインアーキテクチャ」を作成できる。…

rand.Readerはいつエラーを返すのか

概要 golangのuuid生成で有名な satori/go.uuid はこちらのコミットでUUIDv4を生成する際にエラーを返すように変わりました。 理由は github.com このissueに対応するためなのですが、内部で使っているrand.Read()はそもそもどんな時にエラーが起きるのだろ…

Goの実プロジェクトでのエラーハンドリングの悩みどころと解決案

概要 Golangに限らずではありますが レイヤ間のエラー伝搬 外部APIを叩いた時のエラーコードハンドリング HTTPやgRPCとしてレスポンスを返す時のエラーハンドリング で悩むことは多いと思います。 今回はそれの1つの方針を紹介します。 課題 レイヤ間のエラ…

singleflight でキャッシュのOriginへのリクエストを抑制

Go

概要 golangにはsingleflightという重複したの関数呼び出しを抑制する仕組みがあります。 例えばキャッシュが切れた時にOriginへのアクセスが並行して走ってしまうケースでサーバやDBがスローダウンする問題がありますが、こういった時にsingleflightを挟む…

Clean Architecture で実装するときに知っておきたかったこと

概要 developers.cyberagent.co.jp こちらで 課金システムをマイクロサービス化した サービス自体の設計をDDDにした という対応をしました。 当時は試行錯誤の連続でしたが対応から1年程経ち、ある程度設計もfixされてきたので知見をまとめます。

context.WithCancel, WithTimeout で知っておいた方が良いこと

Go

概要 christina04.hatenablog.com でも話したcontext.Contextはタイムアウト、キャンセルなどのハンドリングができて便利ですが、使う際に知っておいた方が良いことをいくつかまとめました。 環境 golang 1.12.0 Tips Q. 親・子の両方でWithTimeoutが設定さ…

gRPC の Unary Interceptor の基本的な使い方

概要 gRPCのInterceptorのClient側、Server側の基本的な使い方を紹介します。 環境 golang 1.12.0 grpc 1.18.0 Interceptorの種類 以下の4つがあります。今回はUnaryの方の使い方を説明します。 サーバサイド UnaryServerInterceptor StreamServerIntercept…

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

Go

概要 christina04.hatenablog.com で書いていなかったことの追加です。 環境 golang 1.11.4 recoverしたあとのエラーハンドリングをどうするか panicをrecoverしたものはいいものの、 func f() { defer func() { if r := recover(); r != nil { fmt.Println(…

Golangの良いところ

Go

概要 Golangの良いところってなんだろう?と思ってまとめます。 多分新しいことを知ったら追記していきます。 よく言われるところ コンパイルが速い JavaやC++に比べてかなり高速です。 メモリ安全 golangはC言語に近いですが、C言語で問題になっていたメモ…

goroutineはなぜ軽量なのか

Go

概要 以前の記事で christina04.hatenablog.com golangはスレッドよりはるかに軽量なgoroutineでC10K問題を解決する、という話をしましたが、goroutineが軽量なのはなぜか?という理由を深掘りしたことがなかったのでしてみました。 環境 golang 1.11.1 Darw…

Golangのpprofの使い方【メモリ編】

概要 前回 christina04.hatenablog.com にてpprofのコマンドラインツールの使い方を説明しました。 今回はメモリについて ケース1:このバッチ処理、メモリすごく喰うけどどこが原因? ケース2:メモリリークしてない? といったところの調査方法を説明し…

Golangのpprofの使い方【コマンドラインツール編】

概要 前回 christina04.hatenablog.com にてpprofの基本的な使い方を説明しました。 今回はさらに詳細に調べるためのコマンドラインツールの使い方を説明します。 環境 golang 1.11.0

Golang 1.11 で導入された ListenConfig を使って SO_REUSEPORT を利用する

概要 先日リリースされた1.11でソケットオプションを設定できるようになりました。 これによってLinux 3.9から導入されたSO_REUSEPORTという、同じポートでbindすることが可能になる機能が利用可能になります。 環境 golang 1.11 macOS 10.13.6 (Darwin Kern…

GolangでVaultを操作

概要 これまで紹介したHashiCorp Vaultの使い方はCLIを使うのがメインでしたが、実際はアプリケーション内で秘密情報を扱うケースが多々あります。 Vaultはgolangのライブラリを提供しているので、様々なログイン方法を紹介しつつ秘密情報にアクセスしてみま…

GoでGraceful Shutdown

Go

概要 以前はGraceful shutdownをするために以下のようなライブラリを使用していました。 github.com しかしながらGo 1.8 からGraceful Shutdown機能が標準で提供されるようになりました。 今回はその導入方法を紹介します。 環境 golang 1.10.3

GolangのRoundTripperとTransport

Go

背景 僕が保守している go-iapというgolangで書いたAppStore, GooglePlay AmazonAppStore用の課金ライブラリ があるのですが、そこに以下のissueがあがっていました。 github.com ざっくり説明すると「GAEでは普通のhttp.Client使えないからカスタムClientサ…