18
8

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

Google Cloud Storage に Write したときは Close の戻り値を必ず確認する

Posted at

Go言語で Google Cloud Storage を扱う cloud.google.com/go/storage という公式のパッケージがあります。

GCS にファイルをアップロードする処理で、io.Writer のインタフェースを経由してデータをアップロードすることになります。

Writer の取得までは以下のようなコード:

client, err := storage.NewClient(ctx)
if err != nil {
    return err
}
bkt := client.Bucket("bucketname")
obj := bkt.Object("filename1")
w := obj.NewWriter(ctx)

そして Write するときに、いつもの癖で以下のように書くと……ダメです:

...
w := obj.NewWriter(ctx)
defer w.Close()

_, err := w.Write([]byte("こんにちは!こんにちは!"))
if err != nil {
    return err
}

// アップロード成功!……とは限らない

ドキュメントを読んでみましょう。
https://godoc.org/cloud.google.com/go/storage#Writer.Write

Write appends to w. It implements the io.Writer interface.

Since writes happen asynchronously, Write may return a nil error even though the write failed (or will fail). Always use the error returned from Writer.Close to determine if the upload was successful.

下の段をGoogle翻訳:

書き込みは非同期的に行われるため、書き込みが失敗した(または失敗する)にもかかわらず、書き込みがnilエラーを返すことがあります。常にアップロードが成功したかどうかを判断するには、Writer.Closeから返されたエラーを使用します。

この通り Close の戻り値を確認する必要があります。書き込みが非同期なのがポイントで、Writer は内部では io.PipeWriter に Write しているだけです。この Pipe に送られたデータは非同期で GCS に送信されます。通信でエラーが発生しても、Write は成功する場合があるのです(というよりは Write はほぼ成功します、オンメモリの操作なので)。

正しくは以下のように Close の戻り値を確認します:

client, err := storage.NewClient(ctx)
if err != nil {
    return err
}
bkt := client.Bucket("bucketname")
obj := bkt.Object("filename1")
w := obj.NewWriter(ctx)

_, err := w.Write([]byte("こんにちは!こんにちは!"))
if err != nil {
    w.Close() // これは要るかどうか?
    return err
}

// このチェックを忘れずに!
if err := w.Close(); err != nil {
    return err
}

// ここまで来たらアップロード成功!
18
8
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
18
8

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?