Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

S3 PutObject is missing a Content-MD5 header when writing to a bucket with a default object lock configuration #1694

Closed
huubvdw opened this issue Dec 18, 2018 · 7 comments
Labels
guidance Question that needs advice or information.

Comments

@huubvdw
Copy link

huubvdw commented Dec 18, 2018

When writing a new object to a bucket with a default object lock configuration, the request will result is a 400 bad request response. InvalidRequest: Content-MD5 HTTP header is required for Put Object requests with Object Lock parameters

I noticed in ApplyChecksumMiddleware the PutObject operation only sets a sha256 content hash header.

As you don't know upfront if a bucket has a object lock configuration, I'm thinking of setting both the sha256 content hash header and the content MD5 header for the PutObject operation.

Any other suggestions?

@diehlaws diehlaws self-assigned this Dec 19, 2018
@diehlaws diehlaws added the feature-request A feature should be added or improved. label Dec 19, 2018
@diehlaws
Copy link
Contributor

Hi @huubvdw, thanks for reaching out to us about this, and for submitting the associated PR #1695. We will review the PR shortly to ensure it is valid to merge.

@howardlopez
Copy link
Contributor

howardlopez commented Dec 20, 2018

@huubvdw, your investigation and PR are appreciated. Unfortunately, PutObject only requires the Content-MD5 header when there are object lock parameters, so we won't be able to accept your PR to change the general PutObject behavior in this way.

S3 and the SDK teams are aware of the issue and have discussed options internally, but for now, you'll have to supply your own ContentMD5 parameter to object lock requests with PutObject. For example:

$client->putObject([
    'Bucket' => 'your_bucket',
    'Key' => 'your_key',
    'Body' => 'your_body',
    'ObjectLockMode' => 'GOVERNANCE',
    'ObjectLockRetainUntilDate' => $someDate
    'ContentMD5' => base64_encode(md5('your_body', true))
]);

@diehlaws diehlaws added guidance Question that needs advice or information. and removed feature-request A feature should be added or improved. labels Jun 14, 2019
@mmomasters
Copy link

Hi everyone, I am having the same issue and was wondering where can I supply my own ContentMD5 parameter for s3fs to work correctly while using guidance ?

I tried s3fs with -o enable_content_md5 with no success

Thank you!

@diehlaws diehlaws removed their assignment Aug 26, 2020
@harshadparekh
Copy link

This suggestion of passing contentMD5 with PutObject() request assumes that the data we want to write as an object in AWS is available as a file locally so that we can pre-compute the MD5 on the content. For cases where we're generating data on the fly and providing it as an input stream to PutObject() request, how do we get the MD5 to pass alongwith? Also, how does this work when using MultiPartUpload for large objects?

@TheJosh
Copy link

TheJosh commented Aug 31, 2021

It appears that the ContentMD5 field is not listed in the SDK Docs:
https://docs.aws.amazon.com/aws-sdk-php/v3/api/api-s3-2006-03-01.html#putobject

Does the field still exist, even though it's not in the docs?

@dean-huczok
Copy link

dean-huczok commented Sep 3, 2021

Can't find it listed but in the PutObjectRequest class there is a MD5Digest property.
You just gotta MD5 hash your file, base64-encode the hash (string), then slap that string into the PutObjectRequest (C#) and it verks!

PutObjectRequest putRequest = new PutObjectRequest
            {
                BucketName = bucketName,
                Key = keyName,
                FilePath = filePath,
                ContentType = "text/plain",
                MD5Digest = base64encodedHashString  // <-- this will become the Content-MD5 header
            };

@burka
Copy link

burka commented Nov 22, 2023

I calculate the MD5 and set it as the header, file by file:

s3cmd put --add-header="Content-MD5: "`cat your-file | openssl dgst -md5 -binary | openssl enc -base64` your-file s3://bucket

Not nice, but works :-)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
guidance Question that needs advice or information.
Projects
None yet
Development

No branches or pull requests

8 participants