Skip to content

Commit 8363be3

Browse files
authored
[s3] Pass object parameters to head_object in exists (#1451)
When using server-side-encryption with customer-provided keys (SSE-C), the head_object call needs the SSE-C key and algorithm - otherwise the call will fail with `botocore.exceptions.ClientError: An error occurred (400) when calling the HeadObject operation: Bad Request` if the file already exists.
1 parent aa8a82e commit 8363be3

File tree

2 files changed

+13
-1
lines changed

2 files changed

+13
-1
lines changed

storages/backends/s3.py

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -581,8 +581,11 @@ def delete(self, name):
581581

582582
def exists(self, name):
583583
name = self._normalize_name(clean_name(name))
584+
params = _filter_download_params(self.get_object_parameters(name))
584585
try:
585-
self.connection.meta.client.head_object(Bucket=self.bucket_name, Key=name)
586+
self.connection.meta.client.head_object(
587+
Bucket=self.bucket_name, Key=name, **params
588+
)
586589
return True
587590
except ClientError as err:
588591
if err.response["ResponseMetadata"]["HTTPStatusCode"] == 404:

tests/test_s3.py

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -502,6 +502,15 @@ def test_storage_exists(self):
502502
Key="file.txt",
503503
)
504504

505+
def test_storage_exists_ssec(self):
506+
params = {"SSECustomerKey": "xyz", "CacheControl": "never"}
507+
self.storage.get_object_parameters = lambda name: params
508+
self.storage.file_overwrite = False
509+
self.assertTrue(self.storage.exists("file.txt"))
510+
self.storage.connection.meta.client.head_object.assert_called_with(
511+
Bucket=self.storage.bucket_name, Key="file.txt", SSECustomerKey="xyz"
512+
)
513+
505514
def test_storage_exists_false(self):
506515
self.storage.connection.meta.client.head_object.side_effect = ClientError(
507516
{"Error": {}, "ResponseMetadata": {"HTTPStatusCode": 404}},

0 commit comments

Comments
 (0)