diff --git a/setup.py b/setup.py index a610533..96391b4 100644 --- a/setup.py +++ b/setup.py @@ -84,7 +84,7 @@ def reqs(f): # -*- Tests Requires -*- -tests_require = reqs('test.txt') + reqs('test_django.txt') +tests_require = ""#reqs('test.txt') + reqs('test_django.txt') # -*- Long Description -*- diff --git a/thorn/conf.py b/thorn/conf.py index bced6af..6280087 100644 --- a/thorn/conf.py +++ b/thorn/conf.py @@ -35,6 +35,7 @@ class Settings(object): default_signal_honors_transaction = False default_hmac_signer = 'thorn.utils.hmac:compat_sign' default_allow_redirects = False + default_raise_http_error = False def __init__(self, app=None): self.app = app_or_default(app or self.app) @@ -107,6 +108,12 @@ def THORN_ALLOW_REDIRECTS(self): return self._get( 'THORN_ALLOW_REDIRECTS', self.default_allow_redirects) + @cached_property + def THORN_RAISE_HTTP_ERROR(self): + # type: () -> bool + return self._get( + 'THORN_RAISE_HTTP_ERROR', self.default_raise_http_error) + def _get(self, key, default=None): # type: (str, Any) -> Any return self._get_lazy(key, lambda: default) diff --git a/thorn/dispatch/celery.py b/thorn/dispatch/celery.py index a514d98..aacae23 100644 --- a/thorn/dispatch/celery.py +++ b/thorn/dispatch/celery.py @@ -10,7 +10,6 @@ __all__ = ['Dispatcher', 'WorkerDispatcher'] - class _CeleryDispatcher(base.Dispatcher): def as_request_group(self, requests): diff --git a/thorn/request.py b/thorn/request.py index dc3407b..9a19d25 100644 --- a/thorn/request.py +++ b/thorn/request.py @@ -9,7 +9,7 @@ from celery import uuid from celery.utils import cached_property -from requests.exceptions import ConnectionError, Timeout +from requests.exceptions import ConnectionError, HTTPError, Timeout from requests.packages.urllib3.util.url import Url, parse_url from vine import maybe_promise, promise from vine.abstract import Thenable, ThenableProxy @@ -127,6 +127,9 @@ def __init__(self, event, data, sender, subscriber, )) if user_agent: self.user_agent = user_agent + self.raise_http_error = self.app.settings.THORN_RAISE_HTTP_ERROR + if self.raise_http_error: + self.connection_errors = (ConnectionError, HTTPError) def validate_recipient(self, url): # type: (str) -> None @@ -142,6 +145,8 @@ def dispatch(self, session=None, propagate=False): self.validate_recipient(self.subscriber.url) with self._finalize_unless_request_error(propagate): self.response = self.post(session=session) + if self.raise_http_error: + self.response.raise_for_status() return self @contextmanager @@ -198,18 +203,35 @@ def post(self, session=None): host, url = self.to_safeurl(self.subscriber.url) with self.session_or_acquire(session) as session: - return session.post( - url=url, - data=self.data, - allow_redirects=self.allow_redirects, - timeout=self.timeout, - headers=self.annotate_headers({ - 'Hook-HMAC': self.sign_request(self.subscriber, self.data), - 'Hook-Subscription': str(self.subscriber.uuid), - 'Host': host, - }), - verify=False, - ) + try: + return session.post( + url=url, + data=self.data, + allow_redirects=self.allow_redirects, + timeout=self.timeout, + headers=self.annotate_headers({ + 'Hook-HMAC': self.sign_request(self.subscriber, self.data), + 'Hook-Subscription': str(self.subscriber.uuid), + 'Host': host, + }), + verify=False, + ) + except requests.exceptions.SSLError as e: + addr = socket.gethostbyname(host) + url = url.replace(addr, host) + + return session.post( + url=url, + data=self.data, + allow_redirects=self.allow_redirects, + timeout=self.timeout, + headers=self.annotate_headers({ + 'Hook-HMAC': self.sign_request(self.subscriber, self.data), + 'Hook-Subscription': str(self.subscriber.uuid), + 'Host': host, + }), + verify=False, + ) def handle_timeout_error(self, exc, propagate=False): # type: (Exception, bool) -> Any