すずけんメモ

技術メモです

aws-cliのs3api put-objectでContent-MD5ヘッダをつける

put-object — AWS CLI 1.9.2 Command Reference をみると --content-md5 オプションがある。 PUT Object - Amazon Simple Storage Service にあるとおり、

To ensure that data is not corrupted traversing the network, use the Content-MD5 header. When you use this header, Amazon S3 checks the object against the provided MD5 value and, if they do not match, returns an error.

ということでオブジェクトの完全性をチェックするには Content-MD5 ヘッダをPutObjectリクエストにつけるとよい。

AWS Developer Forums: awscli put-object --content-md5 trouble ... でもハマっている人がいた。最初 md5 とか md5sum コマンドでやっていたのだが、これだとhexになったのが出てくる。 https://www.ietf.org/rfc/rfc1864.txt にもあるとおり、Content-MD5ヘッダに設定すべきは base64(md5) であり base64(hex(md5)) ではない。ということでこれをまとめて aws s3api put-object をつかって書くと以下の様にして実現できる。

# s3://your-bucket/your-key-prefix/obj に カレントディレクトリのobjをPutObjectする。
aws s3api put-object --bucket your-bucket --key your-key-prefix --content-md5 `openssl dgst -md5 -binary obj | openssl enc -base64` --body obj

APIを適当な言語で使っている場合にはmd5 sumのbinaryをPipeして組み立てればよいのだが、cliだとうっかりハマってしまった。ちなみにresponseのETagはPutしたObjectのmd5 checksumのhexが返ってくるので、これも合わせてチェックするとさらによいだろう。 レスポンスの例は以下のとおり。

{
    "ETag": "\"a41422711fcbb0982991580e0d4799f6\""
}

これは md5sum -q obj の結果と等しくなる。ただしMultipart Uploadの場合には必ずしもそうはならないので、留意すること。