diff options
author | Jordan Cook <jordan.cook@pioneer.com> | 2022-04-22 20:10:57 -0500 |
---|---|---|
committer | Jordan Cook <jordan.cook@pioneer.com> | 2022-05-04 16:17:22 -0500 |
commit | bbd984375d22dedaf33c8d0cad718cc09d072d25 (patch) | |
tree | 37eb6cfad188feefcd18dff05de9e591c7dff1aa /requests_cache/session.py | |
parent | 3aa84ee6724491858a81ce401487fc85d0ee9c9d (diff) | |
download | requests-cache-bbd984375d22dedaf33c8d0cad718cc09d072d25.tar.gz |
Implement Cache-Control: stale-while-revalidate
Diffstat (limited to 'requests_cache/session.py')
-rw-r--r-- | requests_cache/session.py | 19 |
1 files changed, 15 insertions, 4 deletions
diff --git a/requests_cache/session.py b/requests_cache/session.py index 7be3f94..f6a19dd 100644 --- a/requests_cache/session.py +++ b/requests_cache/session.py @@ -1,7 +1,7 @@ """Main classes to add caching features to :py:class:`requests.Session`""" from contextlib import contextmanager, nullcontext from logging import getLogger -from threading import RLock +from threading import RLock, Thread from typing import TYPE_CHECKING, Iterable, MutableMapping, Optional, Union from requests import PreparedRequest @@ -197,10 +197,13 @@ class CacheMixin(MIXIN_BASE): # Handle missing and expired responses based on settings and headers if actions.error_504: response: AnyResponse = get_504_response(request) - elif actions.send_request: - response = self._send_and_cache(request, actions, cached_response, **kwargs) + elif actions.resend_async: + self._resend_async(request, actions, cached_response, **kwargs) + response = cached_response # type: ignore elif actions.resend_request: response = self._resend(request, actions, cached_response, **kwargs) # type: ignore + elif actions.send_request: + response = self._send_and_cache(request, actions, cached_response, **kwargs) else: response = cached_response # type: ignore # Guaranteed to be non-None by this point @@ -256,6 +259,12 @@ class CacheMixin(MIXIN_BASE): except Exception: return self._handle_error(cached_response, actions) + def _resend_async(self, *args, **kwargs): + """Send a non-blocking request to refresh a cached response""" + logger.debug('Using stale response while revalidating') + thread = Thread(target=self._send_and_cache, args=args, kwargs=kwargs) + thread.start() + def _handle_error(self, cached_response: CachedResponse, actions: CacheActions) -> AnyResponse: """Handle a request error based on settings: * Default behavior: re-raise the error @@ -338,8 +347,10 @@ class CachedSession(CacheMixin, OriginalSession): a list of specific headers to match ignored_parameters: Request paramters, headers, and/or JSON body params to exclude from both request matching and cached request data - stale_if_error: Return stale cache data if a new request raises an exception. Optionally + stale_if_error: Return a stale response if a new request raises an exception. Optionally accepts a time value representing maximum staleness to accept. + stale_while_revalidate: Return a stale response initially, while a non-blocking request is + sent to refresh the response for the next time it's requested filter_fn: Response filtering function that indicates whether or not a given response should be cached. See :ref:`custom-filtering` for details. key_fn: Request matching function for generating custom cache keys. See |