cloudtoolbox 0.3.0__tar.gz → 0.5.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/PKG-INFO +1 -1
- cloudtoolbox-0.5.0/cloud/amazon/helpers.py +22 -0
- cloudtoolbox-0.5.0/cloud/amazon/sns.py +32 -0
- cloudtoolbox-0.5.0/cloud/amazon/sqs.py +32 -0
- cloudtoolbox-0.5.0/cloud/google/pubsub.py +27 -0
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/cloud/protocols.py +10 -2
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/cloudtoolbox.egg-info/PKG-INFO +1 -1
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/cloudtoolbox.egg-info/SOURCES.txt +1 -0
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/pyproject.toml +1 -1
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/tests/test_factory.py +8 -0
- cloudtoolbox-0.3.0/cloud/amazon/sns.py +0 -11
- cloudtoolbox-0.3.0/cloud/amazon/sqs.py +0 -11
- cloudtoolbox-0.3.0/cloud/google/pubsub.py +0 -12
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/LICENSE +0 -0
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/README.md +0 -0
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/cloud/__init__.py +0 -0
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/cloud/amazon/__init__.py +0 -0
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/cloud/amazon/s3.py +0 -0
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/cloud/factory.py +0 -0
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/cloud/google/__init__.py +0 -0
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/cloud/google/storage.py +0 -0
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/cloudtoolbox.egg-info/dependency_links.txt +0 -0
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/cloudtoolbox.egg-info/requires.txt +0 -0
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/cloudtoolbox.egg-info/top_level.txt +0 -0
- {cloudtoolbox-0.3.0 → cloudtoolbox-0.5.0}/setup.cfg +0 -0
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
from typing import Mapping, Union
|
|
2
|
+
|
|
3
|
+
DataType = Union[str, bytes, int, float]
|
|
4
|
+
MessageAttributes = Mapping[str, Mapping[str, DataType]]
|
|
5
|
+
|
|
6
|
+
|
|
7
|
+
def build_attributes(data: Mapping[str, DataType]) -> MessageAttributes:
|
|
8
|
+
attrs = {}
|
|
9
|
+
|
|
10
|
+
for key, value in data.items():
|
|
11
|
+
if isinstance(value, str):
|
|
12
|
+
attr = {"StringValue": value, "DataType": "String"}
|
|
13
|
+
elif isinstance(value, bytes):
|
|
14
|
+
attr = {"BinaryValue": value, "DataType": "Binary"}
|
|
15
|
+
elif isinstance(value, (int, float)):
|
|
16
|
+
attr = {"StringValue": str(value), "DataType": "Number"}
|
|
17
|
+
else:
|
|
18
|
+
raise TypeError(f"{value} of type {type(value).__name__} is not supported")
|
|
19
|
+
|
|
20
|
+
attrs[key] = attr
|
|
21
|
+
|
|
22
|
+
return attrs
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import uuid
|
|
2
|
+
from typing import Any, Mapping, Optional
|
|
3
|
+
|
|
4
|
+
import boto3
|
|
5
|
+
|
|
6
|
+
from cloud.amazon import helpers
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
class Publisher:
|
|
10
|
+
def __init__(self, *args: Any, **kwargs: Any):
|
|
11
|
+
self.client = boto3.client("sns", *args, **kwargs)
|
|
12
|
+
|
|
13
|
+
def publish(
|
|
14
|
+
self,
|
|
15
|
+
recipient: str,
|
|
16
|
+
message: str,
|
|
17
|
+
/,
|
|
18
|
+
*,
|
|
19
|
+
group: str = "",
|
|
20
|
+
attrs: Optional[Mapping[str, Any]] = None,
|
|
21
|
+
) -> str:
|
|
22
|
+
kwargs = {}
|
|
23
|
+
|
|
24
|
+
if group:
|
|
25
|
+
kwargs["MessageGroupId"] = group
|
|
26
|
+
kwargs["MessageDeduplicationId"] = str(uuid.uuid4())
|
|
27
|
+
|
|
28
|
+
if attrs:
|
|
29
|
+
kwargs["MessageAttributes"] = helpers.build_attributes(attrs)
|
|
30
|
+
|
|
31
|
+
response = self.client.publish(TargetArn=recipient, Message=message, **kwargs)
|
|
32
|
+
return response["MessageId"]
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import uuid
|
|
2
|
+
from typing import Any, Mapping, Optional
|
|
3
|
+
|
|
4
|
+
import boto3
|
|
5
|
+
|
|
6
|
+
from cloud.amazon import helpers
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
class Publisher:
|
|
10
|
+
def __init__(self, *args: Any, **kwargs: Any):
|
|
11
|
+
self.client = boto3.client("sqs", *args, **kwargs)
|
|
12
|
+
|
|
13
|
+
def publish(
|
|
14
|
+
self,
|
|
15
|
+
recipient: str,
|
|
16
|
+
message: str,
|
|
17
|
+
/,
|
|
18
|
+
*,
|
|
19
|
+
group: str = "",
|
|
20
|
+
attrs: Optional[Mapping[str, Any]] = None,
|
|
21
|
+
) -> str:
|
|
22
|
+
kwargs = {}
|
|
23
|
+
|
|
24
|
+
if group:
|
|
25
|
+
kwargs["MessageGroupId"] = group
|
|
26
|
+
kwargs["MessageDeduplicationId"] = str(uuid.uuid4())
|
|
27
|
+
|
|
28
|
+
if attrs:
|
|
29
|
+
kwargs["MessageAttributes"] = helpers.build_attributes(attrs)
|
|
30
|
+
|
|
31
|
+
response = self.client.send_message(QueueUrl=recipient, MessageBody=message, **kwargs)
|
|
32
|
+
return response["MessageId"]
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
from typing import Any, Mapping, Optional
|
|
2
|
+
|
|
3
|
+
from google.cloud import pubsub_v1
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
class Publisher:
|
|
7
|
+
def __init__(self, *args: Any, **kwargs: Any) -> None:
|
|
8
|
+
self.client = pubsub_v1.PublisherClient(*args, **kwargs)
|
|
9
|
+
|
|
10
|
+
def publish(
|
|
11
|
+
self,
|
|
12
|
+
recipient: str,
|
|
13
|
+
message: str,
|
|
14
|
+
/,
|
|
15
|
+
*,
|
|
16
|
+
group: str = "",
|
|
17
|
+
attrs: Optional[Mapping[str, Any]] = None,
|
|
18
|
+
) -> str:
|
|
19
|
+
kwargs = attrs or {}
|
|
20
|
+
future = self.client.publish(recipient, data=message.encode(), ordering_key=group, **kwargs)
|
|
21
|
+
return future.result()
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
class OrderedPublisher(Publisher):
|
|
25
|
+
def __init__(self, *args: Any, **kwargs: Any) -> None:
|
|
26
|
+
opts = pubsub_v1.types.PublisherOptions(enable_message_ordering=True)
|
|
27
|
+
super().__init__(*args, publisher_options=opts, **kwargs)
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
from typing import Any, Protocol, runtime_checkable
|
|
1
|
+
from typing import Any, Mapping, Optional, Protocol, runtime_checkable
|
|
2
2
|
|
|
3
3
|
|
|
4
4
|
@runtime_checkable
|
|
@@ -25,4 +25,12 @@ class StorageURLSigner(Protocol):
|
|
|
25
25
|
|
|
26
26
|
@runtime_checkable
|
|
27
27
|
class MessagePublisher(Protocol):
|
|
28
|
-
def publish(
|
|
28
|
+
def publish(
|
|
29
|
+
self,
|
|
30
|
+
recipient: str,
|
|
31
|
+
message: str,
|
|
32
|
+
/,
|
|
33
|
+
*,
|
|
34
|
+
group: str = "",
|
|
35
|
+
attrs: Optional[Mapping[str, Any]] = None,
|
|
36
|
+
) -> str: ...
|
|
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "cloudtoolbox"
|
|
7
|
-
version = "0.
|
|
7
|
+
version = "0.5.0"
|
|
8
8
|
description = "Toolbox for the cloud."
|
|
9
9
|
readme = { file = "README.md", content-type = "text/markdown" }
|
|
10
10
|
authors = [{ name = "Dotz Developers", email = "devs-dotz@dotz.com" }]
|
|
@@ -109,6 +109,14 @@ class TestMessagePublisherFactory(unittest.TestCase):
|
|
|
109
109
|
self.assertIsInstance(publisher, MessagePublisher)
|
|
110
110
|
self.assertIsInstance(publisher, pubsub.Publisher)
|
|
111
111
|
|
|
112
|
+
@mock.patch("google.cloud.pubsub_v1.PublisherClient")
|
|
113
|
+
def test_google_ordered_publisher(self, _):
|
|
114
|
+
OrderedPublisher = factory.message_publisher(pubsub.OrderedPublisher)
|
|
115
|
+
publisher = OrderedPublisher()
|
|
116
|
+
|
|
117
|
+
self.assertIsInstance(publisher, MessagePublisher)
|
|
118
|
+
self.assertIsInstance(publisher, pubsub.OrderedPublisher)
|
|
119
|
+
|
|
112
120
|
@mock.patch("boto3.client")
|
|
113
121
|
def test_amazon_publisher(self, _):
|
|
114
122
|
for cls in (sns.Publisher, sqs.Publisher):
|
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
from typing import Any
|
|
2
|
-
|
|
3
|
-
import boto3
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
class Publisher:
|
|
7
|
-
def __init__(self, *args: Any, **kwargs: Any):
|
|
8
|
-
self.client = boto3.client("sns", *args, **kwargs)
|
|
9
|
-
|
|
10
|
-
def publish(self, recipient: str, message: str, **attrs: Any) -> None:
|
|
11
|
-
self.client.publish(TargetArn=recipient, Message=message, **attrs)
|
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
from typing import Any
|
|
2
|
-
|
|
3
|
-
import boto3
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
class Publisher:
|
|
7
|
-
def __init__(self, *args: Any, **kwargs: Any):
|
|
8
|
-
self.client = boto3.client("sqs", *args, **kwargs)
|
|
9
|
-
|
|
10
|
-
def publish(self, recipient: str, message: str, **attrs: Any) -> None:
|
|
11
|
-
self.client.send_message(QueueUrl=recipient, MessageBody=message, **attrs)
|
|
@@ -1,12 +0,0 @@
|
|
|
1
|
-
from typing import Any
|
|
2
|
-
|
|
3
|
-
from google.cloud import pubsub_v1
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
class Publisher:
|
|
7
|
-
def __init__(self, *args: Any, **kwargs: Any) -> None:
|
|
8
|
-
self.client = pubsub_v1.PublisherClient(*args, **kwargs)
|
|
9
|
-
|
|
10
|
-
def publish(self, recipient: str, message: str, **attrs: Any) -> None:
|
|
11
|
-
future = self.client.publish(recipient, data=message.encode(), **attrs)
|
|
12
|
-
future.result()
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|