wazzapi 0.1.0__py3-none-any.whl

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.
@@ -0,0 +1,87 @@
1
+ from __future__ import annotations
2
+
3
+ from datetime import datetime
4
+ from typing import Literal
5
+
6
+ from .base import WazzapiModel
7
+
8
+ MessageWebhookEvent = Literal[
9
+ "message.received",
10
+ "message.sent",
11
+ "message.delivered",
12
+ "message.read",
13
+ "message.failed",
14
+ ]
15
+ DeviceWebhookEvent = Literal["device.connected", "device.disconnected"]
16
+ WebhookEvent = MessageWebhookEvent | DeviceWebhookEvent
17
+
18
+
19
+ class PublicWebhookMessageData(WazzapiModel):
20
+ message_id: str
21
+ whatsapp_message_id: str | None = None
22
+ phone_number: str
23
+ account_name: str | None = None
24
+ status: str
25
+ direction: str
26
+ message_type: str
27
+ failure_reason: str | None = None
28
+ reason: str | None = None
29
+ sent_at: datetime | None = None
30
+ delivered_at: datetime | None = None
31
+ read_at: datetime | None = None
32
+ failed_at: datetime | None = None
33
+ whatsapp_account_id: str
34
+ campaign_id: str | None = None
35
+ batch_id: str | None = None
36
+
37
+
38
+ class PublicWebhookDeviceData(WazzapiModel):
39
+ message_id: str
40
+ whatsapp_message_id: str | None = None
41
+ phone_number: str
42
+ account_name: str | None = None
43
+ status: str
44
+ direction: str
45
+ message_type: str
46
+ failure_reason: str | None = None
47
+ reason: str | None = None
48
+ sent_at: datetime | None = None
49
+ delivered_at: datetime | None = None
50
+ read_at: datetime | None = None
51
+ failed_at: datetime | None = None
52
+ whatsapp_account_id: str
53
+ campaign_id: str | None = None
54
+ batch_id: str | None = None
55
+
56
+
57
+ class PublicMessageWebhook(WazzapiModel):
58
+ id: str
59
+ event_type: MessageWebhookEvent
60
+ timestamp: datetime
61
+ organization_id: str
62
+ webhook_id: str
63
+ data: PublicWebhookMessageData
64
+
65
+
66
+ class PublicDeviceWebhook(WazzapiModel):
67
+ id: str
68
+ event_type: DeviceWebhookEvent
69
+ timestamp: datetime
70
+ organization_id: str
71
+ webhook_id: str
72
+ data: PublicWebhookDeviceData
73
+
74
+
75
+ WebhookPayload = PublicMessageWebhook | PublicDeviceWebhook
76
+
77
+
78
+ __all__ = [
79
+ "DeviceWebhookEvent",
80
+ "MessageWebhookEvent",
81
+ "PublicDeviceWebhook",
82
+ "PublicMessageWebhook",
83
+ "PublicWebhookDeviceData",
84
+ "PublicWebhookMessageData",
85
+ "WebhookEvent",
86
+ "WebhookPayload",
87
+ ]
wazzapi/py.typed ADDED
File without changes
@@ -0,0 +1,5 @@
1
+ from .contacts import ContactsResource
2
+ from .messages import MessagesResource
3
+ from .templates import TemplatesResource
4
+
5
+ __all__ = ["ContactsResource", "MessagesResource", "TemplatesResource"]
@@ -0,0 +1,14 @@
1
+ from __future__ import annotations
2
+
3
+ from typing import TYPE_CHECKING
4
+
5
+ if TYPE_CHECKING:
6
+ from ..client import WazzapiClient
7
+
8
+
9
+ class BaseResource:
10
+ def __init__(self, client: "WazzapiClient") -> None:
11
+ self._client = client
12
+
13
+
14
+ __all__ = ["BaseResource"]
@@ -0,0 +1,222 @@
1
+ from __future__ import annotations
2
+
3
+ from typing import Any
4
+
5
+ from .. import models
6
+ from .base import BaseResource
7
+
8
+
9
+ class ContactsResource(BaseResource):
10
+ def list(
11
+ self,
12
+ *,
13
+ limit: int | None = None,
14
+ offset: int | None = None,
15
+ search: str | None = None,
16
+ source: str | None = None,
17
+ group_id: str | None = None,
18
+ sort_by: str | None = None,
19
+ sort_order: str | None = None,
20
+ ) -> models.ContactListResponse:
21
+ return self._client._request(
22
+ "GET",
23
+ "/api/v1/contacts",
24
+ params={
25
+ "limit": limit,
26
+ "offset": offset,
27
+ "search": search,
28
+ "source": source,
29
+ "group_id": group_id,
30
+ "sort_by": sort_by,
31
+ "sort_order": sort_order,
32
+ },
33
+ response_model=models.ContactListResponse,
34
+ )
35
+
36
+ def create(
37
+ self,
38
+ payload: models.ContactCreateRequest | dict[str, Any],
39
+ ) -> models.ContactResponse:
40
+ return self._client._request(
41
+ "POST",
42
+ "/api/v1/contacts",
43
+ json_body=payload,
44
+ response_model=models.ContactResponse,
45
+ )
46
+
47
+ def bulk_delete(
48
+ self,
49
+ payload: models.BulkDeleteRequest | dict[str, Any],
50
+ ) -> models.BulkDeleteResponse:
51
+ return self._client._request(
52
+ "POST",
53
+ "/api/v1/contacts/bulk-delete",
54
+ json_body=payload,
55
+ response_model=models.BulkDeleteResponse,
56
+ )
57
+
58
+ def list_groups(
59
+ self,
60
+ *,
61
+ limit: int | None = None,
62
+ offset: int | None = None,
63
+ ) -> models.ContactGroupListResponse:
64
+ return self._client._request(
65
+ "GET",
66
+ "/api/v1/contacts/groups",
67
+ params={"limit": limit, "offset": offset},
68
+ response_model=models.ContactGroupListResponse,
69
+ )
70
+
71
+ def create_group(
72
+ self,
73
+ payload: models.ContactGroupCreateRequest | dict[str, Any],
74
+ ) -> models.ContactGroupItem:
75
+ return self._client._request(
76
+ "POST",
77
+ "/api/v1/contacts/groups",
78
+ json_body=payload,
79
+ response_model=models.ContactGroupItem,
80
+ )
81
+
82
+ def get_group(
83
+ self,
84
+ group_id: str,
85
+ *,
86
+ limit: int | None = None,
87
+ offset: int | None = None,
88
+ ) -> models.ContactGroupMembersResponse:
89
+ return self._client._request(
90
+ "GET",
91
+ f"/api/v1/contacts/groups/{group_id}",
92
+ params={"limit": limit, "offset": offset},
93
+ response_model=models.ContactGroupMembersResponse,
94
+ )
95
+
96
+ def update_group(
97
+ self,
98
+ group_id: str,
99
+ payload: models.ContactGroupUpdateRequest | dict[str, Any],
100
+ ) -> models.ContactGroupItem:
101
+ return self._client._request(
102
+ "PATCH",
103
+ f"/api/v1/contacts/groups/{group_id}",
104
+ json_body=payload,
105
+ response_model=models.ContactGroupItem,
106
+ )
107
+
108
+ def delete_group(self, group_id: str) -> None:
109
+ self._client._request("DELETE", f"/api/v1/contacts/groups/{group_id}")
110
+ return None
111
+
112
+ def add_to_group(
113
+ self,
114
+ group_id: str,
115
+ payload: models.AddToGroupRequest | dict[str, Any],
116
+ ) -> models.AddToGroupResponse:
117
+ return self._client._request(
118
+ "POST",
119
+ f"/api/v1/contacts/groups/{group_id}/members",
120
+ json_body=payload,
121
+ response_model=models.AddToGroupResponse,
122
+ )
123
+
124
+ def remove_from_group(
125
+ self,
126
+ group_id: str,
127
+ payload: models.RemoveFromGroupRequest | dict[str, Any],
128
+ ) -> models.AddToGroupResponse:
129
+ return self._client._request(
130
+ "DELETE",
131
+ f"/api/v1/contacts/groups/{group_id}/members",
132
+ json_body=payload,
133
+ response_model=models.AddToGroupResponse,
134
+ )
135
+
136
+ def import_csv(
137
+ self,
138
+ payload: models.CSVImportRequest | dict[str, Any],
139
+ ) -> models.CSVImportResponse:
140
+ return self._client._request(
141
+ "POST",
142
+ "/api/v1/contacts/import/csv",
143
+ json_body=payload,
144
+ response_model=models.CSVImportResponse,
145
+ )
146
+
147
+ def export_csv(
148
+ self,
149
+ *,
150
+ group_id: str | None = None,
151
+ source: str | None = None,
152
+ ) -> models.CSVExportResponse:
153
+ return self._client._request(
154
+ "GET",
155
+ "/api/v1/contacts/export/csv",
156
+ params={"group_id": group_id, "source": source},
157
+ response_model=models.CSVExportResponse,
158
+ )
159
+
160
+ def sync(
161
+ self,
162
+ payload: models.ContactSyncRequest | dict[str, Any],
163
+ ) -> models.ContactSyncResponse:
164
+ return self._client._request(
165
+ "POST",
166
+ "/api/v1/contacts/sync",
167
+ json_body=payload,
168
+ response_model=models.ContactSyncResponse,
169
+ )
170
+
171
+ def sync_status(self) -> list[models.ContactSyncStatusResponse]:
172
+ return self._client._request(
173
+ "GET",
174
+ "/api/v1/contacts/sync/status",
175
+ response_model=list[models.ContactSyncStatusResponse],
176
+ )
177
+
178
+ def sync_history(
179
+ self,
180
+ *,
181
+ limit: int | None = None,
182
+ offset: int | None = None,
183
+ ) -> models.ContactSyncHistoryResponse:
184
+ return self._client._request(
185
+ "GET",
186
+ "/api/v1/contacts/sync/history",
187
+ params={"limit": limit, "offset": offset},
188
+ response_model=models.ContactSyncHistoryResponse,
189
+ )
190
+
191
+ def import_template(self) -> dict[str, Any]:
192
+ return self._client._request(
193
+ "GET",
194
+ "/api/v1/contacts/import/template",
195
+ response_model=dict[str, Any],
196
+ )
197
+
198
+ def get(self, contact_id: str) -> models.ContactResponse:
199
+ return self._client._request(
200
+ "GET",
201
+ f"/api/v1/contacts/{contact_id}",
202
+ response_model=models.ContactResponse,
203
+ )
204
+
205
+ def update(
206
+ self,
207
+ contact_id: str,
208
+ payload: models.ContactUpdateRequest | dict[str, Any],
209
+ ) -> models.ContactResponse:
210
+ return self._client._request(
211
+ "PATCH",
212
+ f"/api/v1/contacts/{contact_id}",
213
+ json_body=payload,
214
+ response_model=models.ContactResponse,
215
+ )
216
+
217
+ def delete(self, contact_id: str) -> None:
218
+ self._client._request("DELETE", f"/api/v1/contacts/{contact_id}")
219
+ return None
220
+
221
+
222
+ __all__ = ["ContactsResource"]
@@ -0,0 +1,174 @@
1
+ from __future__ import annotations
2
+
3
+ from typing import Any
4
+
5
+ from .. import models
6
+ from .base import BaseResource
7
+
8
+
9
+ class MessagesResource(BaseResource):
10
+ def lookup(self, whatsapp_message_id: str) -> models.MessageResponse:
11
+ return self._client._request(
12
+ "GET",
13
+ "/api/v1/messages/lookup",
14
+ params={"whatsapp_message_id": whatsapp_message_id},
15
+ response_model=models.MessageResponse,
16
+ )
17
+
18
+ def list(
19
+ self,
20
+ *,
21
+ limit: int | None = None,
22
+ offset: int | None = None,
23
+ status: str | None = None,
24
+ direction: str | None = None,
25
+ whatsapp_account_id: str | None = None,
26
+ search: str | None = None,
27
+ sort_by: str | None = None,
28
+ sort_order: str | None = None,
29
+ ) -> models.MessageListResponse:
30
+ return self._client._request(
31
+ "GET",
32
+ "/api/v1/messages",
33
+ params={
34
+ "limit": limit,
35
+ "offset": offset,
36
+ "status": status,
37
+ "direction": direction,
38
+ "whatsapp_account_id": whatsapp_account_id,
39
+ "search": search,
40
+ "sort_by": sort_by,
41
+ "sort_order": sort_order,
42
+ },
43
+ response_model=models.MessageListResponse,
44
+ )
45
+
46
+ def get(self, message_id: str) -> models.MessageResponse:
47
+ return self._client._request(
48
+ "GET",
49
+ f"/api/v1/messages/{message_id}",
50
+ response_model=models.MessageResponse,
51
+ )
52
+
53
+ def stats(self) -> models.MessageStatsResponse:
54
+ return self._client._request(
55
+ "GET",
56
+ "/api/v1/messages/stats/summary",
57
+ response_model=models.MessageStatsResponse,
58
+ )
59
+
60
+ def send(
61
+ self,
62
+ payload: models.SendMessageRequest | dict[str, Any],
63
+ ) -> models.SendMessageResponse:
64
+ return self._client._request(
65
+ "POST",
66
+ "/api/v1/messages/send",
67
+ json_body=payload,
68
+ response_model=models.SendMessageResponse,
69
+ )
70
+
71
+ def send_image(
72
+ self,
73
+ payload: models.SendMessageRequest | dict[str, Any],
74
+ ) -> models.SendMessageResponse:
75
+ return self._client._request(
76
+ "POST",
77
+ "/api/v1/messages/send/image",
78
+ json_body=payload,
79
+ response_model=models.SendMessageResponse,
80
+ )
81
+
82
+ def send_video(
83
+ self,
84
+ payload: models.SendMessageRequest | dict[str, Any],
85
+ ) -> models.SendMessageResponse:
86
+ return self._client._request(
87
+ "POST",
88
+ "/api/v1/messages/send/video",
89
+ json_body=payload,
90
+ response_model=models.SendMessageResponse,
91
+ )
92
+
93
+ def send_voice(
94
+ self,
95
+ payload: models.SendMessageRequest | dict[str, Any],
96
+ ) -> models.SendMessageResponse:
97
+ return self._client._request(
98
+ "POST",
99
+ "/api/v1/messages/send/voice",
100
+ json_body=payload,
101
+ response_model=models.SendMessageResponse,
102
+ )
103
+
104
+ def send_document(
105
+ self,
106
+ payload: models.SendMessageRequest | dict[str, Any],
107
+ ) -> models.SendMessageResponse:
108
+ return self._client._request(
109
+ "POST",
110
+ "/api/v1/messages/send/document",
111
+ json_body=payload,
112
+ response_model=models.SendMessageResponse,
113
+ )
114
+
115
+ def send_location(
116
+ self,
117
+ payload: models.SendMessageRequest | dict[str, Any],
118
+ ) -> models.SendMessageResponse:
119
+ return self._client._request(
120
+ "POST",
121
+ "/api/v1/messages/send/location",
122
+ json_body=payload,
123
+ response_model=models.SendMessageResponse,
124
+ )
125
+
126
+ def send_contact(
127
+ self,
128
+ payload: models.SendMessageRequest | dict[str, Any],
129
+ ) -> models.SendMessageResponse:
130
+ return self._client._request(
131
+ "POST",
132
+ "/api/v1/messages/send/contact",
133
+ json_body=payload,
134
+ response_model=models.SendMessageResponse,
135
+ )
136
+
137
+ def retry(self, message_id: str) -> models.RetryMessageResponse:
138
+ return self._client._request(
139
+ "POST",
140
+ f"/api/v1/messages/{message_id}/retry",
141
+ response_model=models.RetryMessageResponse,
142
+ )
143
+
144
+ def cancel(self, message_id: str) -> models.CancelMessageResponse:
145
+ return self._client._request(
146
+ "POST",
147
+ f"/api/v1/messages/{message_id}/cancel",
148
+ response_model=models.CancelMessageResponse,
149
+ )
150
+
151
+ def send_buttons(
152
+ self,
153
+ payload: models.ButtonReplyRequest | dict[str, Any],
154
+ ) -> models.InteractiveMessageResponse:
155
+ return self._client._request(
156
+ "POST",
157
+ "/api/v1/messages/send/interactive/buttons",
158
+ json_body=payload,
159
+ response_model=models.InteractiveMessageResponse,
160
+ )
161
+
162
+ def send_list(
163
+ self,
164
+ payload: models.ListReplyRequest | dict[str, Any],
165
+ ) -> models.InteractiveMessageResponse:
166
+ return self._client._request(
167
+ "POST",
168
+ "/api/v1/messages/send/interactive/list",
169
+ json_body=payload,
170
+ response_model=models.InteractiveMessageResponse,
171
+ )
172
+
173
+
174
+ __all__ = ["MessagesResource"]
@@ -0,0 +1,87 @@
1
+ from __future__ import annotations
2
+
3
+ from typing import Any
4
+
5
+ from .. import models
6
+ from .base import BaseResource
7
+
8
+
9
+ class TemplatesResource(BaseResource):
10
+ def builtin_variables(self) -> models.BuiltinVariablesResponse:
11
+ return self._client._request(
12
+ "GET",
13
+ "/api/v1/templates/builtin-variables",
14
+ response_model=models.BuiltinVariablesResponse,
15
+ )
16
+
17
+ def list(
18
+ self,
19
+ *,
20
+ limit: int | None = None,
21
+ offset: int | None = None,
22
+ category: str | None = None,
23
+ search: str | None = None,
24
+ sort_by: str | None = None,
25
+ sort_order: str | None = None,
26
+ ) -> models.TemplateListResponse:
27
+ return self._client._request(
28
+ "GET",
29
+ "/api/v1/templates",
30
+ params={
31
+ "limit": limit,
32
+ "offset": offset,
33
+ "category": category,
34
+ "search": search,
35
+ "sort_by": sort_by,
36
+ "sort_order": sort_order,
37
+ },
38
+ response_model=models.TemplateListResponse,
39
+ )
40
+
41
+ def create(
42
+ self,
43
+ payload: models.TemplateCreateRequest | dict[str, Any],
44
+ ) -> models.TemplateResponse:
45
+ return self._client._request(
46
+ "POST",
47
+ "/api/v1/templates",
48
+ json_body=payload,
49
+ response_model=models.TemplateResponse,
50
+ )
51
+
52
+ def get(self, template_id: str) -> models.TemplateResponse:
53
+ return self._client._request(
54
+ "GET",
55
+ f"/api/v1/templates/{template_id}",
56
+ response_model=models.TemplateResponse,
57
+ )
58
+
59
+ def update(
60
+ self,
61
+ template_id: str,
62
+ payload: models.TemplateUpdateRequest | dict[str, Any],
63
+ ) -> models.TemplateResponse:
64
+ return self._client._request(
65
+ "PATCH",
66
+ f"/api/v1/templates/{template_id}",
67
+ json_body=payload,
68
+ response_model=models.TemplateResponse,
69
+ )
70
+
71
+ def delete(self, template_id: str) -> None:
72
+ self._client._request("DELETE", f"/api/v1/templates/{template_id}")
73
+ return None
74
+
75
+ def preview(
76
+ self,
77
+ payload: models.TemplatePreviewRequest | dict[str, Any],
78
+ ) -> models.TemplatePreviewResponse:
79
+ return self._client._request(
80
+ "POST",
81
+ "/api/v1/templates/preview",
82
+ json_body=payload,
83
+ response_model=models.TemplatePreviewResponse,
84
+ )
85
+
86
+
87
+ __all__ = ["TemplatesResource"]