Add versionid header in complete multipart if enabled (#3643)
* Add versionid header in complete multipart if enabled - addresses https://github.com/localstack/localstack/issues/3514 * remove unnecessary code * fix lint * fix lint test * add test case for boto3
This commit is contained in:
parent
78a5661093
commit
7d066cea2f
@ -1750,8 +1750,15 @@ class ResponseObject(_TemplateEnvironmentMixin, ActionAuthenticatorMixin):
|
|||||||
upload_id = query["uploadId"][0]
|
upload_id = query["uploadId"][0]
|
||||||
key = self.backend.complete_multipart(bucket_name, upload_id, body)
|
key = self.backend.complete_multipart(bucket_name, upload_id, body)
|
||||||
template = self.response_template(S3_MULTIPART_COMPLETE_RESPONSE)
|
template = self.response_template(S3_MULTIPART_COMPLETE_RESPONSE)
|
||||||
return template.render(
|
headers = {}
|
||||||
|
if key.version_id:
|
||||||
|
headers["x-amz-version-id"] = key.version_id
|
||||||
|
return (
|
||||||
|
200,
|
||||||
|
headers,
|
||||||
|
template.render(
|
||||||
bucket_name=bucket_name, key_name=key.name, etag=key.etag
|
bucket_name=bucket_name, key_name=key.name, etag=key.etag
|
||||||
|
),
|
||||||
)
|
)
|
||||||
elif "restore" in query:
|
elif "restore" in query:
|
||||||
es = minidom.parseString(body).getElementsByTagName("Days")
|
es = minidom.parseString(body).getElementsByTagName("Days")
|
||||||
|
@ -255,6 +255,23 @@ def test_multipart_etag():
|
|||||||
bucket.get_key("the-key").etag.should.equal(EXPECTED_ETAG)
|
bucket.get_key("the-key").etag.should.equal(EXPECTED_ETAG)
|
||||||
|
|
||||||
|
|
||||||
|
@mock_s3_deprecated
|
||||||
|
@reduced_min_part_size
|
||||||
|
def test_multipart_version():
|
||||||
|
# Create Bucket so that test can run
|
||||||
|
conn = boto.connect_s3("the_key", "the_secret")
|
||||||
|
bucket = conn.create_bucket("mybucket")
|
||||||
|
bucket.configure_versioning(versioning=True)
|
||||||
|
multipart = bucket.initiate_multipart_upload("the-key")
|
||||||
|
part1 = b"0" * REDUCED_PART_SIZE
|
||||||
|
multipart.upload_part_from_file(BytesIO(part1), 1)
|
||||||
|
# last part, can be less than 5 MB
|
||||||
|
part2 = b"1"
|
||||||
|
multipart.upload_part_from_file(BytesIO(part2), 2)
|
||||||
|
resp = multipart.complete_upload()
|
||||||
|
resp.version_id.should_not.be.none
|
||||||
|
|
||||||
|
|
||||||
@mock_s3_deprecated
|
@mock_s3_deprecated
|
||||||
@reduced_min_part_size
|
@reduced_min_part_size
|
||||||
def test_multipart_invalid_order():
|
def test_multipart_invalid_order():
|
||||||
@ -2569,6 +2586,54 @@ def test_boto3_multipart_etag():
|
|||||||
resp["ETag"].should.equal(EXPECTED_ETAG)
|
resp["ETag"].should.equal(EXPECTED_ETAG)
|
||||||
|
|
||||||
|
|
||||||
|
@mock_s3
|
||||||
|
@reduced_min_part_size
|
||||||
|
def test_boto3_multipart_version():
|
||||||
|
# Create Bucket so that test can run
|
||||||
|
s3 = boto3.client("s3", region_name=DEFAULT_REGION_NAME)
|
||||||
|
s3.create_bucket(Bucket="mybucket")
|
||||||
|
|
||||||
|
s3.put_bucket_versioning(
|
||||||
|
Bucket="mybucket", VersioningConfiguration={"Status": "Enabled"}
|
||||||
|
)
|
||||||
|
|
||||||
|
upload_id = s3.create_multipart_upload(Bucket="mybucket", Key="the-key")["UploadId"]
|
||||||
|
part1 = b"0" * REDUCED_PART_SIZE
|
||||||
|
etags = []
|
||||||
|
etags.append(
|
||||||
|
s3.upload_part(
|
||||||
|
Bucket="mybucket",
|
||||||
|
Key="the-key",
|
||||||
|
PartNumber=1,
|
||||||
|
UploadId=upload_id,
|
||||||
|
Body=part1,
|
||||||
|
)["ETag"]
|
||||||
|
)
|
||||||
|
# last part, can be less than 5 MB
|
||||||
|
part2 = b"1"
|
||||||
|
etags.append(
|
||||||
|
s3.upload_part(
|
||||||
|
Bucket="mybucket",
|
||||||
|
Key="the-key",
|
||||||
|
PartNumber=2,
|
||||||
|
UploadId=upload_id,
|
||||||
|
Body=part2,
|
||||||
|
)["ETag"]
|
||||||
|
)
|
||||||
|
response = s3.complete_multipart_upload(
|
||||||
|
Bucket="mybucket",
|
||||||
|
Key="the-key",
|
||||||
|
UploadId=upload_id,
|
||||||
|
MultipartUpload={
|
||||||
|
"Parts": [
|
||||||
|
{"ETag": etag, "PartNumber": i} for i, etag in enumerate(etags, 1)
|
||||||
|
]
|
||||||
|
},
|
||||||
|
)
|
||||||
|
|
||||||
|
response["VersionId"].should.should_not.be.none
|
||||||
|
|
||||||
|
|
||||||
@mock_s3
|
@mock_s3
|
||||||
@reduced_min_part_size
|
@reduced_min_part_size
|
||||||
def test_boto3_multipart_part_size():
|
def test_boto3_multipart_part_size():
|
||||||
|
Loading…
Reference in New Issue
Block a user