gpt4 book ai didi

python - requests_cache 是否会在信息更新时自动更新缓存?

转载 作者:行者123 更新时间:2023-12-01 04:48:26 35 4
gpt4 key购买 nike

我使用 Python 请求了一个非常不可靠的 API。我一直在考虑使用requests_cache并将 expire_after 设置为 999999999999 就像我看到其他人所做的那样。唯一的问题是,我不知道 API 何时再次工作,数据是否更新。如果requests_cache会自动自动更新并删除旧条目。

我尝试阅读文档,但我在任何地方都看不到这一点。

最佳答案

requests_cacheexpire_after 时间过后不会更新。在这种情况下,它不会检测到您的 API 已恢复到工作状态。

我注意到该项目添加了一个我过去实现过的选项;您现在可以在配置缓存时设置 old_data_on_error 选项;请参阅CachedSession documentation :

old_data_on_error – If True it will return expired cached response if update fails.

如果后端更新失败,它将重用现有的缓存数据,而不是删除该数据。

过去,我创建了自己的 requests_cache session 设置(加上小补丁),如果后端给出 500 错误或超时,它将重用 expire_after 之外的缓存值(使用短超时)处理有问题的 API 层,而不是依赖 expire_after:

import logging

from datetime import (
datetime,
timedelta
)
from requests.exceptions import (
ConnectionError,
Timeout,
)
from requests_cache.core import (
dispatch_hook,
CachedSession,
)

log = logging.getLogger(__name__)
# Stop logging from complaining if no logging has been configured.
log.addHandler(logging.NullHandler())


class FallbackCachedSession(CachedSession):
"""Cached session that'll reuse expired cache data on timeouts

This allows survival in case the backend is down, living of stale
data until it comes back.

"""

def send(self, request, **kwargs):
# this *bypasses* CachedSession.send; we want to call the method
# CachedSession.send() would have delegated to!
session_send = super(CachedSession, self).send
if (self._is_cache_disabled or
request.method not in self._cache_allowable_methods):
response = session_send(request, **kwargs)
response.from_cache = False
return response

cache_key = self.cache.create_key(request)

def send_request_and_cache_response(stale=None):
try:
response = session_send(request, **kwargs)
except (Timeout, ConnectionError):
if stale is None:
raise
log.warning('No response received, reusing stale response for '
'%s', request.url)
return stale

if stale is not None and response.status_code == 500:
log.warning('Response gave 500 error, reusing stale response '
'for %s', request.url)
return stale

if response.status_code in self._cache_allowable_codes:
self.cache.save_response(cache_key, response)
response.from_cache = False
return response

response, timestamp = self.cache.get_response_and_time(cache_key)
if response is None:
return send_request_and_cache_response()

if self._cache_expire_after is not None:
is_expired = datetime.utcnow() - timestamp > self._cache_expire_after
if is_expired:
self.cache.delete(cache_key)
# try and get a fresh response, but if that fails reuse the
# stale one
return send_request_and_cache_response(stale=response)

# dispatch hook here, because we've removed it before pickling
response.from_cache = True
response = dispatch_hook('response', request.hooks, response, **kwargs)
return response


def basecache_delete(self, key):
# We don't really delete; we instead set the timestamp to
# datetime.min. This way we can re-use stale values if the backend
# fails
try:
if key not in self.responses:
key = self.keys_map[key]
self.responses[key] = self.responses[key][0], datetime.min
except KeyError:
return

from requests_cache.backends.base import BaseCache
BaseCache.delete = basecache_delete

上述CachedSession的子类绕过original send() method相反,直接转到原始的 requests.Session.send() 方法,即使超时已过但后端失败,也返回现有的缓存值。删除被禁用,有利于将超时值设置为 0,因此如果新请求失败,我们仍然可以重用旧值。

使用 FallbackCachedSession 而不是常规的 CachedSession 对象。

如果您想使用 requests_cache.install_cache(),请确保在 session_factory 关键字参数中将 FallbackCachedSession 传递给该函数:

import requests_cache

requests_cache.install_cache(
'cache_name', backend='some_backend', expire_after=180,
session_factory=FallbackCachedSession)

我的方法比我将上述内容组合在一起一段时间后实现的 requests_cache 更全面一些;即使您之前明确将其标记为已删除,我的版本也会回退到过时的响应。

关于python - requests_cache 是否会在信息更新时自动更新缓存?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28918086/

35 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com