Skip to content

Commit

Permalink
Remove scheme from bucket_host
Browse files Browse the repository at this point in the history
The `fastenv.cloud.object_storage.ObjectStorageConfig` class is used to
configure fastenv for connecting to object storage buckets. The class
accepts a `bucket_host` in "virtual-hosted-style," like
`<BUCKET_NAME>.s3.<REGION>.amazonaws.com` for AWS S3 or
`<BUCKET_NAME>.s3.<REGION>.backblazeb2.com` for Backblaze B2.

Object storage buckets commonly have HTTPS endpoints, and therefore some
users may prepend the scheme ("https://") to their `bucket_host`. The
scheme should be removed if present because it is added automatically
when generating instances of `httpx.URL()`.

This commit will update
`fastenv.cloud.object_storage.ObjectStorageConfig` to remove the scheme.

https://docs.aws.amazon.com/AmazonS3/latest/userguide/VirtualHosting.html
  • Loading branch information
br3ndonland committed Jan 14, 2024
1 parent 0f2c1bb commit 9232d8f
Show file tree
Hide file tree
Showing 2 changed files with 34 additions and 7 deletions.
16 changes: 12 additions & 4 deletions fastenv/cloud/object_storage.py
Original file line number Diff line number Diff line change
Expand Up @@ -77,10 +77,18 @@ def __init__(
"`<BUCKET_NAME>.s3.<REGION>.backblazeb2.com` for Backblaze B2."
)
elif bucket_host and not bucket_name:
if (
bucket_host.endswith(".amazonaws.com")
or bucket_host.endswith(".backblazeb2.com")
) and bucket_name is None:
scheme = (
"http://"
if bucket_host.startswith("http://")
else "https://"
if bucket_host.startswith("https://")
else None
)
if scheme:
bucket_host = bucket_host.split(scheme, maxsplit=1)[1]
if bucket_host.endswith(".amazonaws.com") or bucket_host.endswith(
".backblazeb2.com"
):
self.bucket_name = bucket_host.split(".s3.")[0]
else:
self.bucket_name = None
Expand Down
25 changes: 22 additions & 3 deletions tests/cloud/test_object_storage.py
Original file line number Diff line number Diff line change
Expand Up @@ -243,10 +243,10 @@ def test_config_if_not_bucket_name(
bucket_name=bucket_name,
bucket_region=bucket_region,
)
if "backblazeb2" in bucket_host and bucket_name is None:
assert config.bucket_name == "mybucket"
else:
if "digitaloceanspaces.com" in bucket_host:
assert config.bucket_name is None
else:
assert config.bucket_name == self.example_bucket_name

def test_config_if_bucket_name_not_in_bucket_host(
self, mocker: MockerFixture
Expand Down Expand Up @@ -295,6 +295,25 @@ def test_config_if_bucket_region_not_in_bucket_host(
)
assert str(e.value) == expected_exception_value

@pytest.mark.parametrize("scheme", ("http", "https"))
def test_config_if_scheme_in_bucket_host(
self, scheme: str, mocker: MockerFixture
) -> None:
"""Assert that bucket host scheme ("http" or "https") is removed if present.
Scheme is added automatically when generating instances of `httpx.URL()`.
"""
mocker.patch.dict(os.environ, clear=True)
bucket_host = f"{scheme}://{self.example_bucket_host}"
expected_bucket_host = self.example_bucket_host
config = fastenv.cloud.object_storage.ObjectStorageConfig(
access_key=self.example_access_key,
secret_key=self.example_secret_key,
bucket_host=bucket_host,
bucket_region=self.example_bucket_region,
)
assert self.config_is_correct(config, expected_bucket_host=expected_bucket_host)
assert scheme not in config.bucket_host


class TestObjectStorageClientUnit:
"""Test `class ObjectStorageClient` and its methods.
Expand Down

0 comments on commit 9232d8f

Please sign in to comment.