Skip to content

Commit

Permalink
[server] default callback url registration delay to 3 sec
Browse files Browse the repository at this point in the history
  • Loading branch information
david-lev committed Jul 26, 2024
1 parent e831c30 commit a109a71
Show file tree
Hide file tree
Showing 3 changed files with 19 additions and 19 deletions.
15 changes: 9 additions & 6 deletions pywa/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,8 @@

_logger = logging.getLogger(__name__)

_DEFAULT_VERIFY_DELAY_SEC = 3


class WhatsApp(Server, HandlerDecorators):
def __init__(
Expand All @@ -82,7 +84,7 @@ def __init__(
fields: Iterable[str] | None = None,
app_id: int | None = None,
app_secret: str | None = None,
verify_timeout: int | None = None,
verify_timeout: int = _DEFAULT_VERIFY_DELAY_SEC,
business_private_key: str | None = None,
business_private_key_password: str | None = None,
flows_request_decryptor: utils.FlowRequestDecryptor
Expand Down Expand Up @@ -131,12 +133,12 @@ def __init__(
use a custom session, e.g. for proxy support. Do not use the same session across multiple WhatsApp clients!).
server: The Flask or FastAPI app instance to use for the webhook. required when you want to handle incoming
updates.
callback_url: The callback URL of the server to register (optional, only if you want pywa to register the callback URL for
callback_url: The callback URL of the server (itself) to register (optional, only if you want pywa to register the callback URL for
you).
verify_token: The verify token of the registered ``callback_url`` (Required when ``server`` is provided.
The verify token can be any string. It is used to challenge the webhook endpoint to verify that the
endpoint is valid).
verify_timeout: The timeout (in seconds) to wait for the verify token to be sent to the server (optional,
verify_timeout: The delay (in seconds, default to 3) to wait for the verify token to be sent to the server (optional,
for cases where the server/network is slow or the server is taking a long time to start).
fields: The fields to register for the callback URL (optional, if not provided, all supported fields will be
registered. modify this if you want to reduce the number of unused requests to your server).
Expand All @@ -145,7 +147,7 @@ def __init__(
(optional, required when registering a ``callback_url``).
app_secret: The secret of the app in the
`App Basic Settings <https://developers.facebook.com/docs/development/create-an-app/app-dashboard/basic-settings>`_
(optional, required when registering a ``callback_url``).
(optional, recomended for validating updates, required when registering a ``callback_url``).
webhook_endpoint: The endpoint to listen for incoming messages (if you're using the server for another purpose,
or for multiple WhatsApp clients, you can change this to avoid conflicts).
filter_updates: Whether to filter out user updates that are not sent to this phone_id (default: ``True``, does
Expand All @@ -158,7 +160,7 @@ def __init__(
flows_response_encryptor: The global flows response encryptor implementation to use to encrypt Flows responses.
continue_handling: Whether to continue handling updates after a handler has been found (default: ``True``).
skip_duplicate_updates: Whether to skip duplicate updates (default: ``True``).
validate_updates: Whether to validate updates payloads (default: ``True``).
validate_updates: Whether to validate updates payloads (default: ``True``, ``app_secret`` required).
"""
if not token:
raise ValueError(
Expand Down Expand Up @@ -198,7 +200,8 @@ def __init__(
app_id=app_id,
app_secret=app_secret,
verify_token=verify_token,
verify_timeout=verify_timeout,
verify_timeout=verify_timeout
or _DEFAULT_VERIFY_DELAY_SEC, # backwards compatibility for None
business_private_key=business_private_key,
business_private_key_password=business_private_key_password,
flows_request_decryptor=flows_request_decryptor,
Expand Down
9 changes: 3 additions & 6 deletions pywa/server.py
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,6 @@
if TYPE_CHECKING:
from .client import WhatsApp

_VERIFY_TIMEOUT_SEC = 6

_MESSAGE_TYPES: dict[MessageType, type[Handler]] = {
MessageType.BUTTON: CallbackButtonHandler,
Expand Down Expand Up @@ -145,9 +144,7 @@ def __init__(
app_secret=app_secret,
verify_token=verify_token,
fields=tuple(fields or Handler._fields_to_subclasses().keys()),
delay=(verify_timeout - _VERIFY_TIMEOUT_SEC)
if verify_timeout is not None and verify_timeout > _VERIFY_TIMEOUT_SEC
else 0,
delay=verify_timeout,
)

async def webhook_challenge_handler(self, vt: str, ch: str) -> tuple[str, int]:
Expand Down Expand Up @@ -483,7 +480,6 @@ def _register_callback_url(
app_access_token = self.api.get_app_access_token(
app_id=app_id, app_secret=app_secret
)
# noinspection PyProtectedMember
if not self.api.set_app_callback_url(
app_id=app_id,
app_access_token=app_access_token["access_token"],
Expand All @@ -495,7 +491,8 @@ def _register_callback_url(
_logger.info("Callback URL '%s' registered successfully", callback_url)
except errors.WhatsAppError as e:
raise RuntimeError(
f"Failed to register callback URL '{callback_url}'"
f"Failed to register callback URL '{callback_url}'. if you are using a slow/custom server, you can "
"increase the delay using the `verify_timeout` parameter when initializing the WhatsApp client."
) from e

def get_flow_request_handler(
Expand Down
14 changes: 7 additions & 7 deletions pywa_async/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
_get_media_msg,
_get_flow_fields,
_media_types_default_filenames,
_DEFAULT_VERIFY_DELAY_SEC,
) # noqa MUST BE IMPORTED FIRST
from .handlers import (
MessageHandler,
Expand All @@ -31,7 +32,6 @@

import logging
import dataclasses
import functools
import hashlib
import json
import mimetypes
Expand Down Expand Up @@ -108,7 +108,7 @@ def __init__(
fields: Iterable[str] | None = None,
app_id: int | None = None,
app_secret: str | None = None,
verify_timeout: int | None = None,
verify_timeout: int = _DEFAULT_VERIFY_DELAY_SEC,
business_private_key: str | None = None,
business_private_key_password: str | None = None,
flows_request_decryptor: utils.FlowRequestDecryptor
Expand Down Expand Up @@ -165,12 +165,12 @@ def __init__(
use a custom session, e.g. for proxy support. Do not use the same session across multiple WhatsApp clients!).
server: The Flask or FastAPI app instance to use for the webhook. required when you want to handle incoming
updates.
callback_url: The callback URL of the server to register (optional, only if you want pywa to register the callback URL for
callback_url: The callback URL of the server (itself) to register (optional, only if you want pywa to register the callback URL for
you).
verify_token: The verify token of the registered ``callback_url`` (Required when ``server`` is provided.
The verify token can be any string. It is used to challenge the webhook endpoint to verify that the
endpoint is valid).
verify_timeout: The timeout (in seconds) to wait for the verify token to be sent to the server (optional,
verify_timeout: The delay (in seconds, default to 3) to wait for the verify token to be sent to the server (optional,
for cases where the server/network is slow or the server is taking a long time to start).
fields: The fields to register for the callback URL (optional, if not provided, all supported fields will be
registered. modify this if you want to reduce the number of unused requests to your server).
Expand All @@ -179,12 +179,12 @@ def __init__(
(optional, required when registering a ``callback_url``).
app_secret: The secret of the app in the
`App Basic Settings <https://developers.facebook.com/docs/development/create-an-app/app-dashboard/basic-settings>`_
(optional, required when registering a ``callback_url``).
(optional, recomended for validating updates, required when registering a ``callback_url``).
webhook_endpoint: The endpoint to listen for incoming messages (if you're using the server for another purpose,
or for multiple WhatsApp clients, you can change this to avoid conflicts).
you can change this to avoid conflicts).
filter_updates: Whether to filter out user updates that are not sent to this phone_id (default: ``True``, does
not apply to raw updates or updates that are not user-related).
validate_updates: Whether to validate updates payloads (default: ``True``).
validate_updates: Whether to validate updates payloads (default: ``True``, ``app_secret`` required).
business_account_id: The WhatsApp business account ID that owns the phone ID (optional, required for some API
methods).
business_private_key: The global private key to use in the ``flows_request_decryptor``
Expand Down

0 comments on commit a109a71

Please sign in to comment.