Script 'mail_helper' called by obssrc
Hello community,
here is the log from the commit of package python-CacheControl for
openSUSE:Factory checked in at 2021-12-09 19:45:09
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/python-CacheControl (Old)
and /work/SRC/openSUSE:Factory/.python-CacheControl.new.2520 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "python-CacheControl"
Thu Dec 9 19:45:09 2021 rev:9 rq:935720 version:0.12.10
Changes:
--------
--- /work/SRC/openSUSE:Factory/python-CacheControl/python-CacheControl.changes
2020-06-10 00:44:49.218395200 +0200
+++
/work/SRC/openSUSE:Factory/.python-CacheControl.new.2520/python-CacheControl.changes
2021-12-09 19:45:19.281124939 +0100
@@ -1,0 +2,7 @@
+Sat Dec 4 21:10:51 UTC 2021 - Ben Greiner <[email protected]>
+
+- Update to v0.12.10
+ * Dropped support for Python 2.7, 3.4, 3.5.
+ * Reduced memory usage when caching large files.
+
+-------------------------------------------------------------------
Old:
----
CacheControl-0.12.6.tar.gz
New:
----
CacheControl-0.12.10.tar.gz
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Other differences:
------------------
++++++ python-CacheControl.spec ++++++
--- /var/tmp/diff_new_pack.9ysOS8/_old 2021-12-09 19:45:19.949125260 +0100
+++ /var/tmp/diff_new_pack.9ysOS8/_new 2021-12-09 19:45:19.949125260 +0100
@@ -1,7 +1,7 @@
#
# spec file for package python-CacheControl
#
-# Copyright (c) 2020 SUSE LLC
+# Copyright (c) 2021 SUSE LLC
#
# All modifications and additions to the file contributed by third parties
# remain the property of their copyright owners, unless otherwise agreed
@@ -16,9 +16,10 @@
#
-%{?!python_module:%define python_module() python-%{**} python3-%{**}}
+%{?!python_module:%define python_module() python3-%{**}}
+%define skip_python2 1
Name: python-CacheControl
-Version: 0.12.6
+Version: 0.12.10
Release: 0
Summary: Caching library for Python requests
License: Apache-2.0
@@ -28,22 +29,21 @@
BuildRequires: %{python_module setuptools}
BuildRequires: fdupes
BuildRequires: python-rpm-macros
-Requires: python-msgpack
+Requires: python-msgpack >= 0.5.2
Requires: python-requests
+Provides: python-cachecontrol = %{version}-%{release}
Requires(post): update-alternatives
-Requires(postun): update-alternatives
+Requires(postun):update-alternatives
Recommends: python-lockfile >= 0.9
Suggests: python-redis >= 2.10.5
BuildArch: noarch
# SECTION test requirements
-## cherrypy is python3 only from 18.x series
-BuildRequires: python3-CherryPy
-BuildRequires: python3-lockfile >= 0.9
-BuildRequires: python3-mock
-BuildRequires: python3-msgpack
-BuildRequires: python3-pytest
-BuildRequires: python3-redis >= 2.10.5
-BuildRequires: python3-requests
+BuildRequires: %{python_module CherryPy}
+BuildRequires: %{python_module lockfile >= 0.9}
+BuildRequires: %{python_module msgpack >= 0.5.2}
+BuildRequires: %{python_module pytest}
+BuildRequires: %{python_module redis >= 2.10.5}
+BuildRequires: %{python_module requests}
# /SECTION
%python_subpackages
@@ -53,6 +53,7 @@
%prep
%setup -q -n cachecontrol-%{version}
+sed -i -e 's/^from mock/from unittest.mock/' -e 's/^import mock/from unittest
import mock/' tests/*.py
%build
%python_build
@@ -64,7 +65,7 @@
%check
# test_file_cache_recognizes_consumed_file_handle uses httpbin.org directly
-PYTHONPATH=%{buildroot}%{python3_sitelib} py.test-%{python3_bin_suffix} -v -k
'not test_file_cache_recognizes_consumed_file_handle'
+%pytest -v -k 'not test_file_cache_recognizes_consumed_file_handle'
%post
%python_install_alternative doesitcache
@@ -76,6 +77,7 @@
%license LICENSE.txt
%doc README.rst
%python_alternative %{_bindir}/doesitcache
-%{python_sitelib}/*
+%{python_sitelib}/cachecontrol
+%{python_sitelib}/CacheControl-%{version}*-info
%changelog
++++++ CacheControl-0.12.6.tar.gz -> CacheControl-0.12.10.tar.gz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/.bumpversion.cfg
new/cachecontrol-0.12.10/.bumpversion.cfg
--- old/cachecontrol-0.12.6/.bumpversion.cfg 2019-12-22 18:43:35.000000000
+0100
+++ new/cachecontrol-0.12.10/.bumpversion.cfg 2021-11-05 18:07:09.000000000
+0100
@@ -1,6 +1,5 @@
[bumpversion]
-current_version = 0.12.6
+current_version = 0.12.10
files = setup.py cachecontrol/__init__.py docs/conf.py
commit = True
tag = True
-
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/.github/workflows/tests.yml
new/cachecontrol-0.12.10/.github/workflows/tests.yml
--- old/cachecontrol-0.12.6/.github/workflows/tests.yml 1970-01-01
01:00:00.000000000 +0100
+++ new/cachecontrol-0.12.10/.github/workflows/tests.yml 2021-11-05
18:07:09.000000000 +0100
@@ -0,0 +1,34 @@
+---
+name: CI
+
+on:
+ push:
+ branches: ["master"]
+ pull_request:
+ branches: ["master"]
+ workflow_dispatch:
+
+jobs:
+ tests:
+ name: "Python ${{ matrix.python-version }} ${{ matrix.os }}"
+ runs-on: "${{ matrix.os }}"
+
+ strategy:
+ matrix:
+ python-version: ["3.6", "3.7", "3.8", "3.9", "3.10"]
+ os: ["macos-10.15", "windows-latest", "ubuntu-latest"]
+
+ steps:
+ - uses: "actions/checkout@v2"
+ - uses: "actions/setup-python@v2"
+ with:
+ python-version: "${{ matrix.python-version }}"
+ - name: "Install dependencies"
+ run: |
+ python -VV
+ python -m site
+ python -m pip install --upgrade pip setuptools wheel
+ python -m pip install --upgrade virtualenv tox tox-gh-actions
+
+ - name: "Run tox targets for ${{ matrix.python-version }}"
+ run: "python -m tox"
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/.gitignore
new/cachecontrol-0.12.10/.gitignore
--- old/cachecontrol-0.12.6/.gitignore 2019-12-22 18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/.gitignore 2021-11-05 18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
.DS_Store
*.pyc
*.pyo
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/.travis.yml
new/cachecontrol-0.12.10/.travis.yml
--- old/cachecontrol-0.12.6/.travis.yml 2019-12-22 18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/.travis.yml 1970-01-01 01:00:00.000000000
+0100
@@ -1,13 +0,0 @@
-language: python
-sudo: false
-
-python:
- - 2.7
- - 3.4
- - 3.5
- - 3.6
- # - 3.7
-
-install: pip install tox-travis
-
-script: tox
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/CONTRIBUTORS.rst
new/cachecontrol-0.12.10/CONTRIBUTORS.rst
--- old/cachecontrol-0.12.6/CONTRIBUTORS.rst 2019-12-22 18:43:35.000000000
+0100
+++ new/cachecontrol-0.12.10/CONTRIBUTORS.rst 2021-11-05 18:07:09.000000000
+0100
@@ -1,3 +1,8 @@
+..
+ SPDX-FileCopyrightText: SPDX-FileCopyrightText: 2015 Eric Larson
+
+ SPDX-License-Identifier: Apache-2.0
+
==============
Contributors
==============
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/LICENSE.txt
new/cachecontrol-0.12.10/LICENSE.txt
--- old/cachecontrol-0.12.6/LICENSE.txt 2019-12-22 18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/LICENSE.txt 2021-11-05 18:07:09.000000000
+0100
@@ -1,4 +1,4 @@
-Copyright 2015 Eric Larson
+Copyright 2012-2021 Eric Larson
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -8,8 +8,6 @@
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
-WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
-implied.
-
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/MANIFEST.in
new/cachecontrol-0.12.10/MANIFEST.in
--- old/cachecontrol-0.12.6/MANIFEST.in 2019-12-22 18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/MANIFEST.in 1970-01-01 01:00:00.000000000
+0100
@@ -1 +0,0 @@
-include LICENSE.txt
\ No newline at end of file
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/Makefile
new/cachecontrol-0.12.10/Makefile
--- old/cachecontrol-0.12.6/Makefile 2019-12-22 18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/Makefile 2021-11-05 18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
VENV=.venv
VENV_CMD=python3 -m venv
ACTIVATE = $(VENV)/bin/activate
@@ -5,11 +9,11 @@
BUMPTYPE=patch
-$(VENV)/bin/pip:
+$(VENV)/bin/pip3:
$(VENV_CMD) $(VENV)
-bootstrap: $(VENV)/bin/pip
- $(VENV)/bin/pip install -r dev_requirements.txt
+bootstrap: $(VENV)/bin/pip3
+ $(VENV)/bin/pip3 install -r dev_requirements.txt
format:
$(VENV)/bin/black .
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/README.rst
new/cachecontrol-0.12.10/README.rst
--- old/cachecontrol-0.12.6/README.rst 2019-12-22 18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/README.rst 2021-11-05 18:07:09.000000000 +0100
@@ -1,3 +1,8 @@
+..
+ SPDX-FileCopyrightText: SPDX-FileCopyrightText: 2015 Eric Larson
+
+ SPDX-License-Identifier: Apache-2.0
+
==============
CacheControl
==============
@@ -38,5 +43,5 @@
For more info, check out the docs_
.. _docs: http://cachecontrol.readthedocs.org/en/latest/
-.. _httplib2: https://github.com/jcgregorio/httplib2
+.. _httplib2: https://github.com/httplib2/httplib2
.. _requests: http://docs.python-requests.org/
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/cachecontrol/__init__.py
new/cachecontrol-0.12.10/cachecontrol/__init__.py
--- old/cachecontrol-0.12.6/cachecontrol/__init__.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/cachecontrol/__init__.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,11 +1,18 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
"""CacheControl import Interface.
Make it easy to import from cachecontrol without long namespaces.
"""
__author__ = "Eric Larson"
__email__ = "[email protected]"
-__version__ = "0.12.6"
+__version__ = "0.12.10"
from .wrapper import CacheControl
from .adapter import CacheControlAdapter
from .controller import CacheController
+
+import logging
+logging.getLogger(__name__).addHandler(logging.NullHandler())
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/cachecontrol/_cmd.py
new/cachecontrol-0.12.10/cachecontrol/_cmd.py
--- old/cachecontrol-0.12.6/cachecontrol/_cmd.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/cachecontrol/_cmd.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
import logging
import requests
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/cachecontrol/adapter.py
new/cachecontrol-0.12.10/cachecontrol/adapter.py
--- old/cachecontrol-0.12.6/cachecontrol/adapter.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/cachecontrol/adapter.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,16 +1,20 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
import types
import functools
import zlib
from requests.adapters import HTTPAdapter
-from .controller import CacheController
+from .controller import CacheController, PERMANENT_REDIRECT_STATUSES
from .cache import DictCache
from .filewrapper import CallbackFileWrapper
class CacheControlAdapter(HTTPAdapter):
- invalidating_methods = {"PUT", "DELETE"}
+ invalidating_methods = {"PUT", "PATCH", "DELETE"}
def __init__(
self,
@@ -93,7 +97,7 @@
response = cached_response
# We always cache the 301 responses
- elif response.status == 301:
+ elif int(response.status) in PERMANENT_REDIRECT_STATUSES:
self.controller.cache_response(request, response)
else:
# Wrap the response file with a wrapper that will cache the
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/cachecontrol/cache.py
new/cachecontrol-0.12.10/cachecontrol/cache.py
--- old/cachecontrol-0.12.6/cachecontrol/cache.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/cachecontrol/cache.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
"""
The cache object API for implementing caches. The default is a thread
safe in-memory dictionary.
@@ -10,7 +14,7 @@
def get(self, key):
raise NotImplementedError()
- def set(self, key, value):
+ def set(self, key, value, expires=None):
raise NotImplementedError()
def delete(self, key):
@@ -29,7 +33,7 @@
def get(self, key):
return self.data.get(key, None)
- def set(self, key, value):
+ def set(self, key, value, expires=None):
with self.lock:
self.data.update({key: value})
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/cachecontrol/caches/__init__.py
new/cachecontrol-0.12.10/cachecontrol/caches/__init__.py
--- old/cachecontrol-0.12.6/cachecontrol/caches/__init__.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/cachecontrol/caches/__init__.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,2 +1,6 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
from .file_cache import FileCache # noqa
from .redis_cache import RedisCache # noqa
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/cachecontrol-0.12.6/cachecontrol/caches/file_cache.py
new/cachecontrol-0.12.10/cachecontrol/caches/file_cache.py
--- old/cachecontrol-0.12.6/cachecontrol/caches/file_cache.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/cachecontrol/caches/file_cache.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
import hashlib
import os
from textwrap import dedent
@@ -114,7 +118,7 @@
except FileNotFoundError:
return None
- def set(self, key, value):
+ def set(self, key, value, expires=None):
name = self._fn(key)
# Make sure the directory exists
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/cachecontrol-0.12.6/cachecontrol/caches/redis_cache.py
new/cachecontrol-0.12.10/cachecontrol/caches/redis_cache.py
--- old/cachecontrol-0.12.6/cachecontrol/caches/redis_cache.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/cachecontrol/caches/redis_cache.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
from __future__ import division
from datetime import datetime
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/cachecontrol/compat.py
new/cachecontrol-0.12.10/cachecontrol/compat.py
--- old/cachecontrol-0.12.6/cachecontrol/compat.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/cachecontrol/compat.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
try:
from urllib.parse import urljoin
except ImportError:
@@ -9,7 +13,6 @@
except ImportError:
import pickle
-
# Handle the case where the requests module has been patched to not have
# urllib3 bundled as part of its source.
try:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/cachecontrol/controller.py
new/cachecontrol-0.12.10/cachecontrol/controller.py
--- old/cachecontrol-0.12.6/cachecontrol/controller.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/cachecontrol/controller.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
"""
The httplib2 algorithms ported for use with requests.
"""
@@ -17,6 +21,8 @@
URI = re.compile(r"^(([^:/?#]+):)?(//([^/?#]*))?([^?#]*)(\?([^#]*))?(#(.*))?")
+PERMANENT_REDIRECT_STATUSES = (301, 308)
+
def parse_uri(uri):
"""Parses a URI using the regex given in Appendix B of RFC 3986.
@@ -37,7 +43,7 @@
self.cache = DictCache() if cache is None else cache
self.cache_etags = cache_etags
self.serializer = serializer or Serializer()
- self.cacheable_status_codes = status_codes or (200, 203, 300, 301)
+ self.cacheable_status_codes = status_codes or (200, 203, 300, 301, 308)
@classmethod
def _urlnorm(cls, uri):
@@ -147,17 +153,18 @@
logger.warning("Cache entry deserialization failed, entry ignored")
return False
- # If we have a cached 301, return it immediately. We don't
- # need to test our response for other headers b/c it is
+ # If we have a cached permanent redirect, return it immediately. We
+ # don't need to test our response for other headers b/c it is
# intrinsically "cacheable" as it is Permanent.
+ #
# See:
# https://tools.ietf.org/html/rfc7231#section-6.4.2
#
# Client can try to refresh the value by repeating the request
# with cache busting headers as usual (ie no-cache).
- if resp.status == 301:
+ if int(resp.status) in PERMANENT_REDIRECT_STATUSES:
msg = (
- 'Returning cached "301 Moved Permanently" response '
+ "Returning cached permanent redirect response "
"(ignoring date and etag information)"
)
logger.debug(msg)
@@ -261,6 +268,11 @@
response_headers = CaseInsensitiveDict(response.headers)
+ if "date" in response_headers:
+ date = calendar.timegm(parsedate_tz(response_headers["date"]))
+ else:
+ date = 0
+
# If we've been given a body, our response has a Content-Length, that
# Content-Length is valid then we can check to see if the body we've
# been given matches the expected size, and if it doesn't we'll just
@@ -304,35 +316,62 @@
# If we've been given an etag, then keep the response
if self.cache_etags and "etag" in response_headers:
+ expires_time = 0
+ if response_headers.get("expires"):
+ expires = parsedate_tz(response_headers["expires"])
+ if expires is not None:
+ expires_time = calendar.timegm(expires) - date
+
+ expires_time = max(expires_time, 14 * 86400)
+
+ logger.debug("etag object cached for {0}
seconds".format(expires_time))
logger.debug("Caching due to etag")
self.cache.set(
- cache_url, self.serializer.dumps(request, response, body=body)
+ cache_url,
+ self.serializer.dumps(request, response, body),
+ expires=expires_time,
)
- # Add to the cache any 301s. We do this before looking that
- # the Date headers.
- elif response.status == 301:
- logger.debug("Caching permanant redirect")
- self.cache.set(cache_url, self.serializer.dumps(request, response))
+ # Add to the cache any permanent redirects. We do this before looking
+ # that the Date headers.
+ elif int(response.status) in PERMANENT_REDIRECT_STATUSES:
+ logger.debug("Caching permanent redirect")
+ self.cache.set(cache_url, self.serializer.dumps(request, response,
b""))
# Add to the cache if the response headers demand it. If there
# is no date header then we can't do anything about expiring
# the cache.
elif "date" in response_headers:
+ date = calendar.timegm(parsedate_tz(response_headers["date"]))
# cache when there is a max-age > 0
if "max-age" in cc and cc["max-age"] > 0:
logger.debug("Caching b/c date exists and max-age > 0")
+ expires_time = cc["max-age"]
self.cache.set(
- cache_url, self.serializer.dumps(request, response,
body=body)
+ cache_url,
+ self.serializer.dumps(request, response, body),
+ expires=expires_time,
)
# If the request can expire, it means we should cache it
# in the meantime.
elif "expires" in response_headers:
if response_headers["expires"]:
- logger.debug("Caching b/c of expires header")
+ expires = parsedate_tz(response_headers["expires"])
+ if expires is not None:
+ expires_time = calendar.timegm(expires) - date
+ else:
+ expires_time = None
+
+ logger.debug(
+ "Caching b/c of expires header. expires in {0}
seconds".format(
+ expires_time
+ )
+ )
self.cache.set(
- cache_url, self.serializer.dumps(request, response,
body=body)
+ cache_url,
+ self.serializer.dumps(request, response, body=body),
+ expires=expires_time,
)
def update_cached_response(self, request, response):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/cachecontrol/filewrapper.py
new/cachecontrol-0.12.10/cachecontrol/filewrapper.py
--- old/cachecontrol-0.12.6/cachecontrol/filewrapper.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/cachecontrol/filewrapper.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,4 +1,9 @@
-from io import BytesIO
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
+from tempfile import NamedTemporaryFile
+import mmap
class CallbackFileWrapper(object):
@@ -11,10 +16,17 @@
This class uses members with a double underscore (__) leading prefix so as
not to accidentally shadow an attribute.
+
+ The data is stored in a temporary file until it is all available. As long
+ as the temporary files directory is disk-based (sometimes it's a
+ memory-backed-``tmpfs`` on Linux), data will be unloaded to disk if memory
+ pressure is high. For small files the disk usually won't be used at all,
+ it'll all be in the filesystem memory cache, so there should be no
+ performance impact.
"""
def __init__(self, fp, callback):
- self.__buf = BytesIO()
+ self.__buf = NamedTemporaryFile("rb+", delete=True)
self.__fp = fp
self.__callback = callback
@@ -49,7 +61,19 @@
def _close(self):
if self.__callback:
- self.__callback(self.__buf.getvalue())
+ if self.__buf.tell() == 0:
+ # Empty file:
+ result = b""
+ else:
+ # Return the data without actually loading it into memory,
+ # relying on Python's buffer API and mmap(). mmap() just gives
+ # a view directly into the filesystem's memory cache, so it
+ # doesn't result in duplicate memory use.
+ self.__buf.seek(0, 0)
+ result = memoryview(
+ mmap.mmap(self.__buf.fileno(), 0, access=mmap.ACCESS_READ)
+ )
+ self.__callback(result)
# We assign this to None here, because otherwise we can get into
# really tricky problems where the CPython interpreter dead locks
@@ -58,9 +82,16 @@
# and allows the garbage collector to do it's thing normally.
self.__callback = None
+ # Closing the temporary file releases memory and frees disk space.
+ # Important when caching big files.
+ self.__buf.close()
+
def read(self, amt=None):
data = self.__fp.read(amt)
- self.__buf.write(data)
+ if data:
+ # We may be dealing with b'', a sign that things are over:
+ # it's passed e.g. after we've already closed self.__buf.
+ self.__buf.write(data)
if self.__is_fp_closed():
self._close()
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/cachecontrol/heuristics.py
new/cachecontrol-0.12.10/cachecontrol/heuristics.py
--- old/cachecontrol-0.12.6/cachecontrol/heuristics.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/cachecontrol/heuristics.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
import calendar
import time
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/cachecontrol/serialize.py
new/cachecontrol-0.12.10/cachecontrol/serialize.py
--- old/cachecontrol-0.12.6/cachecontrol/serialize.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/cachecontrol/serialize.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
import base64
import io
import json
@@ -17,24 +21,18 @@
return _b64_decode_bytes(s).decode("utf8")
-class Serializer(object):
+_default_body_read = object()
+
+class Serializer(object):
def dumps(self, request, response, body=None):
response_headers = CaseInsensitiveDict(response.headers)
if body is None:
+ # When a body isn't passed in, we'll read the response. We
+ # also update the response with a new file handler to be
+ # sure it acts as though it was never read.
body = response.read(decode_content=False)
-
- # NOTE: 99% sure this is dead code. I'm only leaving it
- # here b/c I don't have a test yet to prove
- # it. Basically, before using
- # `cachecontrol.filewrapper.CallbackFileWrapper`,
- # this made an effort to reset the file handle. The
- # `CallbackFileWrapper` short circuits this code by
- # setting the body as the content is consumed, the
- # result being a `body` argument is *always* passed
- # into cache_response, and in turn,
- # `Serializer.dump`.
response._fp = io.BytesIO(body)
# NOTE: This is all a bit weird, but it's really important that on
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/cachecontrol/wrapper.py
new/cachecontrol-0.12.10/cachecontrol/wrapper.py
--- old/cachecontrol-0.12.6/cachecontrol/wrapper.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/cachecontrol/wrapper.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
from .adapter import CacheControlAdapter
from .cache import DictCache
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/dev_requirements.txt
new/cachecontrol-0.12.10/dev_requirements.txt
--- old/cachecontrol-0.12.6/dev_requirements.txt 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/dev_requirements.txt 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
-e .
tox
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/docs/Makefile
new/cachecontrol-0.12.10/docs/Makefile
--- old/cachecontrol-0.12.6/docs/Makefile 2019-12-22 18:43:35.000000000
+0100
+++ new/cachecontrol-0.12.10/docs/Makefile 2021-11-05 18:07:09.000000000
+0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
# Makefile for Sphinx documentation
#
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/docs/conf.py
new/cachecontrol-0.12.10/docs/conf.py
--- old/cachecontrol-0.12.6/docs/conf.py 2019-12-22 18:43:35.000000000
+0100
+++ new/cachecontrol-0.12.10/docs/conf.py 2021-11-05 18:07:09.000000000
+0100
@@ -1,5 +1,9 @@
# -*- coding: utf-8 -*-
+
+# SPDX-FileCopyrightText: 2015 Eric Larson
#
+# SPDX-License-Identifier: Apache-2.0
+
# CacheControl documentation build configuration file, created by
# sphinx-quickstart on Mon Nov 4 15:01:23 2013.
#
@@ -48,9 +52,9 @@
# built documents.
#
# The short X.Y version.
-version = "0.12.6"
+version = "0.12.10"
# The full version, including alpha/beta/rc tags.
-release = "0.12.6"
+release = "0.12.10"
# The language for content autogenerated by Sphinx. Refer to documentation
# for a list of supported languages.
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/docs/custom_heuristics.rst
new/cachecontrol-0.12.10/docs/custom_heuristics.rst
--- old/cachecontrol-0.12.6/docs/custom_heuristics.rst 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/docs/custom_heuristics.rst 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,8 @@
+..
+ SPDX-FileCopyrightText: SPDX-FileCopyrightText: 2015 Eric Larson
+
+ SPDX-License-Identifier: Apache-2.0
+
===========================
Custom Caching Strategies
===========================
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/docs/etags.rst
new/cachecontrol-0.12.10/docs/etags.rst
--- old/cachecontrol-0.12.6/docs/etags.rst 2019-12-22 18:43:35.000000000
+0100
+++ new/cachecontrol-0.12.10/docs/etags.rst 2021-11-05 18:07:09.000000000
+0100
@@ -1,3 +1,8 @@
+..
+ SPDX-FileCopyrightText: SPDX-FileCopyrightText: 2015 Eric Larson
+
+ SPDX-License-Identifier: Apache-2.0
+
==============
ETag Support
==============
@@ -5,8 +10,8 @@
CacheControl's support of ETags is slightly different than
httplib2. In httplib2, an ETag is considered when using a cached
response when the cache is considered stale. When a cached response is
-expired and it has an ETag header, it returns a response with the
-appropriate `If-None-Match` header. We'll call this behavior a **Time
+expired and it has an ETag header, httplib2 issues the next request with
+the appropriate `If-None-Match` header. We'll call this behavior a **Time
Priority** cache as the ETag support only takes effect when the time has
expired.
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/docs/index.rst
new/cachecontrol-0.12.10/docs/index.rst
--- old/cachecontrol-0.12.6/docs/index.rst 2019-12-22 18:43:35.000000000
+0100
+++ new/cachecontrol-0.12.10/docs/index.rst 2021-11-05 18:07:09.000000000
+0100
@@ -1,3 +1,8 @@
+..
+ SPDX-FileCopyrightText: SPDX-FileCopyrightText: 2015 Eric Larson
+
+ SPDX-License-Identifier: Apache-2.0
+
.. CacheControl documentation master file, created by
sphinx-quickstart on Mon Nov 4 15:01:23 2013.
You can adapt this file completely to your liking, but it should at least
@@ -67,7 +72,7 @@
If you give it a try, please let me know of any issues.
-.. _httplib2: http://code.google.com/p/httplib2/
+.. _httplib2: https://github.com/httplib2/httplib2
.. _requests: http://docs.python-requests.org/
.. _Editing the Web: http://www.w3.org/1999/04/Editing/
.. _PyPI: https://pypi.python.org/pypi/CacheControl/
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/docs/release_notes.rst
new/cachecontrol-0.12.10/docs/release_notes.rst
--- old/cachecontrol-0.12.6/docs/release_notes.rst 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/docs/release_notes.rst 2021-11-05
18:07:09.000000000 +0100
@@ -1,7 +1,18 @@
+..
+ SPDX-FileCopyrightText: SPDX-FileCopyrightText: 2015 Eric Larson
+
+ SPDX-License-Identifier: Apache-2.0
+
===============
Release Notes
===============
+0.13.0
+======
+
+* Dropped support for Python 2.7, 3.4, 3.5.
+* Reduced memory usage when caching large files.
+
0.12.0
======
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/docs/storage.rst
new/cachecontrol-0.12.10/docs/storage.rst
--- old/cachecontrol-0.12.6/docs/storage.rst 2019-12-22 18:43:35.000000000
+0100
+++ new/cachecontrol-0.12.10/docs/storage.rst 2021-11-05 18:07:09.000000000
+0100
@@ -1,3 +1,8 @@
+..
+ SPDX-FileCopyrightText: SPDX-FileCopyrightText: 2015 Eric Larson
+
+ SPDX-License-Identifier: Apache-2.0
+
====================
Storing Cache Data
====================
@@ -105,7 +110,7 @@
-.. _httplib2: http://code.google.com/p/httplib2/
+.. _httplib2: https://github.com/httplib2/httplib2
.. _lockfile: https://github.com/smontanaro/pylockfile
.. _requests 2.1:
http://docs.python-requests.org/en/latest/community/updates/#id2
.. _redis: https://github.com/andymccurdy/redis-py
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/docs/tips.rst
new/cachecontrol-0.12.10/docs/tips.rst
--- old/cachecontrol-0.12.6/docs/tips.rst 2019-12-22 18:43:35.000000000
+0100
+++ new/cachecontrol-0.12.10/docs/tips.rst 2021-11-05 18:07:09.000000000
+0100
@@ -1,3 +1,8 @@
+..
+ SPDX-FileCopyrightText: SPDX-FileCopyrightText: 2015 Eric Larson
+
+ SPDX-License-Identifier: Apache-2.0
+
=========================
Tips and Best Practices
=========================
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/docs/usage.rst
new/cachecontrol-0.12.10/docs/usage.rst
--- old/cachecontrol-0.12.6/docs/usage.rst 2019-12-22 18:43:35.000000000
+0100
+++ new/cachecontrol-0.12.10/docs/usage.rst 2021-11-05 18:07:09.000000000
+0100
@@ -1,3 +1,8 @@
+..
+ SPDX-FileCopyrightText: SPDX-FileCopyrightText: 2015 Eric Larson
+
+ SPDX-License-Identifier: Apache-2.0
+
====================
Using CacheControl
====================
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/examples/benchmark.py
new/cachecontrol-0.12.10/examples/benchmark.py
--- old/cachecontrol-0.12.6/examples/benchmark.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/examples/benchmark.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
import sys
import requests
import argparse
@@ -34,7 +38,7 @@
proc.start()
start = datetime.now()
- for i in xrange(0, 1000):
+ for i in range(0, 1000):
sess.get(URL)
sys.stdout.write(".")
end = datetime.now()
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/setup.cfg
new/cachecontrol-0.12.10/setup.cfg
--- old/cachecontrol-0.12.6/setup.cfg 2019-12-22 18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/setup.cfg 2021-11-05 18:07:09.000000000 +0100
@@ -1,3 +1,11 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
+[metadata]
+license_files =
+ LICENSE.txt
+
[tool:pytest]
norecursedirs = bin lib include build
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/setup.py
new/cachecontrol-0.12.10/setup.py
--- old/cachecontrol-0.12.6/setup.py 2019-12-22 18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/setup.py 2021-11-05 18:07:09.000000000 +0100
@@ -1,8 +1,12 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
import setuptools
long_description = open("README.rst").read()
-VERSION = "0.12.6"
+VERSION = "0.12.10"
setup_params = dict(
name="CacheControl",
@@ -20,18 +24,17 @@
install_requires=["requests", "msgpack>=0.5.2"],
extras_require={"filecache": ["lockfile>=0.9"], "redis":
["redis>=2.10.5"]},
entry_points={"console_scripts": ["doesitcache = cachecontrol._cmd:main"]},
- python_requires=">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*",
+ python_requires=">=3.6",
classifiers=[
"Development Status :: 4 - Beta",
"Environment :: Web Environment",
"License :: OSI Approved :: Apache Software License",
"Operating System :: OS Independent",
- "Programming Language :: Python :: 2",
- "Programming Language :: Python :: 2.7",
- "Programming Language :: Python :: 3",
- "Programming Language :: Python :: 3.4",
- "Programming Language :: Python :: 3.5",
"Programming Language :: Python :: 3.6",
+ "Programming Language :: Python :: 3.7",
+ "Programming Language :: Python :: 3.8",
+ "Programming Language :: Python :: 3.9",
+ "Programming Language :: Python :: 3.10",
"Topic :: Internet :: WWW/HTTP",
],
)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/conftest.py
new/cachecontrol-0.12.10/tests/conftest.py
--- old/cachecontrol-0.12.6/tests/conftest.py 2019-12-22 18:43:35.000000000
+0100
+++ new/cachecontrol-0.12.10/tests/conftest.py 2021-11-05 18:07:09.000000000
+0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
from pprint import pformat
import os
@@ -69,6 +73,11 @@
start_response("200 OK", headers)
return [pformat(env).encode("utf8")]
+ def cache_60(self, env, start_response):
+ headers = [("Cache-Control", "public, max-age=60")]
+ start_response("200 OK", headers)
+ return [pformat(env).encode("utf8")]
+
def no_cache(self, env, start_response):
headers = [("Cache-Control", "no-cache")]
start_response("200 OK", headers)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/issue_263.py
new/cachecontrol-0.12.10/tests/issue_263.py
--- old/cachecontrol-0.12.6/tests/issue_263.py 1970-01-01 01:00:00.000000000
+0100
+++ new/cachecontrol-0.12.10/tests/issue_263.py 2021-11-05 18:07:09.000000000
+0100
@@ -0,0 +1,50 @@
+#!/usr/bin/env python3
+import sys
+
+import cachecontrol
+import requests
+from cachecontrol.cache import DictCache
+from cachecontrol.heuristics import BaseHeuristic
+
+import logging
+
+clogger = logging.getLogger("cachecontrol")
+clogger.addHandler(logging.StreamHandler())
+clogger.setLevel(logging.DEBUG)
+
+
+from pprint import pprint
+
+
+class NoAgeHeuristic(BaseHeuristic):
+ def update_headers(self, response):
+ if "cache-control" in response.headers:
+ del response.headers["cache-control"]
+
+
+cache_adapter = cachecontrol.CacheControlAdapter(
+ DictCache(), cache_etags=True, heuristic=NoAgeHeuristic()
+)
+
+
+session = requests.Session()
+session.mount("https://", cache_adapter)
+
+
+def log_resp(resp):
+ return
+
+ print(f"{resp.status_code} {resp.request.method}")
+ for k, v in response.headers.items():
+ print(f"{k}: {v}")
+
+
+for i in range(2):
+ response = session.get(
+ "https://api.github.com/repos/sigmavirus24/github3.py/pulls/1033"
+ )
+ log_resp(response)
+ print(f"Content length: {len(response.content)}")
+ print(response.from_cache)
+ if len(response.content) == 0:
+ sys.exit(1)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/test_adapter.py
new/cachecontrol-0.12.10/tests/test_adapter.py
--- old/cachecontrol-0.12.6/tests/test_adapter.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/tests/test_adapter.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
import mock
import pytest
@@ -45,6 +49,11 @@
sess.get(url)
assert not r2.from_cache
+ def test_patch_invalidates_cache(self, url, sess):
+ r2 = sess.patch(url, data={"foo": "bar"})
+ sess.get(url)
+ assert not r2.from_cache
+
def test_delete_invalidates_cache(self, url, sess):
r2 = sess.delete(url)
sess.get(url)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/test_cache_control.py
new/cachecontrol-0.12.10/tests/test_cache_control.py
--- old/cachecontrol-0.12.6/tests/test_cache_control.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/tests/test_cache_control.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
"""
Unit tests that verify our caching methods work correctly.
"""
@@ -67,7 +71,7 @@
# When the body is the wrong size, then we don't want to cache it
# because it is obviously broken.
resp = self.resp({"cache-control": "max-age=3600", "Content-Length":
"5"})
- cc.cache_response(self.req(), resp, body=b"0" * 10)
+ cc.cache_response(self.req(), resp, b"0" * 10)
assert not cc.cache.set.called
@@ -82,8 +86,8 @@
resp = self.resp({"cache-control": "max-age=3600", "date": now})
req = self.req()
cc.cache_response(req, resp)
- cc.serializer.dumps.assert_called_with(req, resp, body=None)
- cc.cache.set.assert_called_with(self.url, ANY)
+ cc.serializer.dumps.assert_called_with(req, resp, None)
+ cc.cache.set.assert_called_with(self.url, ANY, expires=3600)
def test_cache_response_cache_max_age_with_invalid_value_not_cached(self,
cc):
now = time.strftime(TIME_FMT, time.gmtime())
@@ -133,7 +137,7 @@
# skip our in/out processing
cc.serializer = Mock()
cc.serializer.loads.return_value = cached_resp
- cc.cache_url = Mock(return_value="http://foo.com")
+ cc.cache_url = Mock(return_value=self.url)
result = cc.update_cached_response(Mock(), resp)
@@ -152,7 +156,7 @@
return self.c.cached_request(mock_request)
def test_cache_request_no_headers(self):
- cached_resp = Mock(headers={"ETag": "jfd9094r808", "Content-Length":
100})
+ cached_resp = Mock(headers={"ETag": "jfd9094r808", "Content-Length":
100}, status=200)
self.c.cache = DictCache({self.url: cached_resp})
resp = self.req({})
assert not resp
@@ -179,7 +183,7 @@
def test_cache_request_fresh_max_age(self):
now = time.strftime(TIME_FMT, time.gmtime())
- resp = Mock(headers={"cache-control": "max-age=3600", "date": now})
+ resp = Mock(headers={"cache-control": "max-age=3600", "date": now},
status=200)
cache = DictCache({self.url: resp})
self.c.cache = cache
@@ -189,7 +193,7 @@
def test_cache_request_unfresh_max_age(self):
earlier = time.time() - 3700 # epoch - 1h01m40s
now = time.strftime(TIME_FMT, time.gmtime(earlier))
- resp = Mock(headers={"cache-control": "max-age=3600", "date": now})
+ resp = Mock(headers={"cache-control": "max-age=3600", "date": now},
status=200)
self.c.cache = DictCache({self.url: resp})
r = self.req({})
assert not r
@@ -198,7 +202,7 @@
later = time.time() + 86400 # GMT + 1 day
expires = time.strftime(TIME_FMT, time.gmtime(later))
now = time.strftime(TIME_FMT, time.gmtime())
- resp = Mock(headers={"expires": expires, "date": now})
+ resp = Mock(headers={"expires": expires, "date": now}, status=200)
cache = DictCache({self.url: resp})
self.c.cache = cache
r = self.req({})
@@ -208,7 +212,7 @@
sooner = time.time() - 86400 # GMT - 1 day
expires = time.strftime(TIME_FMT, time.gmtime(sooner))
now = time.strftime(TIME_FMT, time.gmtime())
- resp = Mock(headers={"expires": expires, "date": now})
+ resp = Mock(headers={"expires": expires, "date": now}, status=200)
cache = DictCache({self.url: resp})
self.c.cache = cache
r = self.req({})
@@ -217,7 +221,7 @@
def test_cached_request_with_bad_max_age_headers_not_returned(self):
now = time.strftime(TIME_FMT, time.gmtime())
# Not a valid header; this would be from a misconfigured server
- resp = Mock(headers={"cache-control": "max-age=xxx", "date": now})
+ resp = Mock(headers={"cache-control": "max-age=xxx", "date": now},
status=200)
self.c.cache = DictCache({self.url: resp})
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/test_chunked_response.py
new/cachecontrol-0.12.10/tests/test_chunked_response.py
--- old/cachecontrol-0.12.6/tests/test_chunked_response.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/tests/test_chunked_response.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,6 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
"""
Test for supporting streamed responses (Transfer-Encoding: chunked)
"""
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/test_etag.py
new/cachecontrol-0.12.10/tests/test_etag.py
--- old/cachecontrol-0.12.6/tests/test_etag.py 2019-12-22 18:43:35.000000000
+0100
+++ new/cachecontrol-0.12.10/tests/test_etag.py 2021-11-05 18:07:09.000000000
+0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
import pytest
from mock import Mock, patch
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/test_expires_heuristics.py
new/cachecontrol-0.12.10/tests/test_expires_heuristics.py
--- old/cachecontrol-0.12.6/tests/test_expires_heuristics.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/tests/test_expires_heuristics.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
import calendar
import time
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/test_max_age.py
new/cachecontrol-0.12.10/tests/test_max_age.py
--- old/cachecontrol-0.12.6/tests/test_max_age.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/tests/test_max_age.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
from __future__ import print_function
import pytest
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/test_redirects.py
new/cachecontrol-0.12.10/tests/test_redirects.py
--- old/cachecontrol-0.12.6/tests/test_redirects.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/tests/test_redirects.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
"""
Test for supporting redirect caches as needed.
"""
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/test_regressions.py
new/cachecontrol-0.12.10/tests/test_regressions.py
--- old/cachecontrol-0.12.6/tests/test_regressions.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/tests/test_regressions.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
import sys
import pytest
@@ -13,10 +17,11 @@
@pytest.mark.skipif(
sys.version.startswith("2"), reason="Only run this for python 3.x"
)
- def test_file_cache_recognizes_consumed_file_handle(self):
+ def test_file_cache_recognizes_consumed_file_handle(self, url):
s = CacheControl(Session(), FileCache("web_cache"))
- s.get("http://httpbin.org/cache/60")
- r = s.get("http://httpbin.org/cache/60")
+ the_url = url + "cache_60"
+ s.get(the_url)
+ r = s.get(the_url)
assert r.from_cache
s.close()
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/test_serialization.py
new/cachecontrol-0.12.10/tests/test_serialization.py
--- old/cachecontrol-0.12.6/tests/test_serialization.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/tests/test_serialization.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
import msgpack
import requests
@@ -8,7 +12,6 @@
class TestSerializer(object):
-
def setup(self):
self.serializer = Serializer()
self.response_data = {
@@ -89,7 +92,9 @@
original_resp = requests.get(url, stream=True)
req = original_resp.request
- resp = self.serializer.loads(req, self.serializer.dumps(req,
original_resp.raw))
+ resp = self.serializer.loads(
+ req, self.serializer.dumps(req, original_resp.raw,
original_resp.content)
+ )
assert resp.read()
@@ -99,7 +104,7 @@
req = original_resp.request
resp = self.serializer.loads(
- req, self.serializer.dumps(req, original_resp.raw, body=data)
+ req, self.serializer.dumps(req, original_resp.raw, data)
)
assert resp.read() == data
@@ -114,5 +119,19 @@
original_resp.raw.headers["vary"] = "Foo"
assert self.serializer.loads(
- req, self.serializer.dumps(req, original_resp.raw, body=data)
+ req, self.serializer.dumps(req, original_resp.raw, data)
)
+
+ def test_no_body_creates_response_file_handle_on_dumps(self, url):
+ original_resp = requests.get(url, stream=True)
+ data = None
+ req = original_resp.request
+
+ assert self.serializer.loads(
+ req, self.serializer.dumps(req, original_resp.raw, data)
+ )
+
+ # By passing in data=None it will force a read of the file
+ # handle. Reading it again proves we're resetting the internal
+ # file handle with a buffer.
+ assert original_resp.raw.read()
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/cachecontrol-0.12.6/tests/test_server_http_version.py
new/cachecontrol-0.12.10/tests/test_server_http_version.py
--- old/cachecontrol-0.12.6/tests/test_server_http_version.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/tests/test_server_http_version.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
import requests
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/test_storage_filecache.py
new/cachecontrol-0.12.10/tests/test_storage_filecache.py
--- old/cachecontrol-0.12.6/tests/test_storage_filecache.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/tests/test_storage_filecache.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
"""
Unit tests that verify FileCache storage works correctly.
"""
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/test_storage_redis.py
new/cachecontrol-0.12.10/tests/test_storage_redis.py
--- old/cachecontrol-0.12.6/tests/test_storage_redis.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/tests/test_storage_redis.py 2021-11-05
18:07:09.000000000 +0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
from datetime import datetime
from mock import Mock
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/test_stream.py
new/cachecontrol-0.12.10/tests/test_stream.py
--- old/cachecontrol-0.12.6/tests/test_stream.py 2019-12-22
18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/tests/test_stream.py 1970-01-01
01:00:00.000000000 +0100
@@ -1,23 +0,0 @@
-"""
-Test for supporting streamed responses (Transfer-Encoding: chunked)
-"""
-import requests
-
-from cachecontrol import CacheControl
-
-
-class TestStream(object):
-
- def setup(self):
- self.sess = CacheControl(requests.Session())
-
- def test_stream_is_cached(self, url):
- resp_1 = self.sess.get(url + "stream")
- content_1 = resp_1.content
-
- resp_2 = self.sess.get(url + "stream")
- content_2 = resp_1.content
-
- assert not resp_1.from_cache
- assert resp_2.from_cache
- assert content_1 == content_2
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tests/test_vary.py
new/cachecontrol-0.12.10/tests/test_vary.py
--- old/cachecontrol-0.12.6/tests/test_vary.py 2019-12-22 18:43:35.000000000
+0100
+++ new/cachecontrol-0.12.10/tests/test_vary.py 2021-11-05 18:07:09.000000000
+0100
@@ -1,3 +1,7 @@
+# SPDX-FileCopyrightText: 2015 Eric Larson
+#
+# SPDX-License-Identifier: Apache-2.0
+
import pytest
import requests
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/cachecontrol-0.12.6/tox.ini
new/cachecontrol-0.12.10/tox.ini
--- old/cachecontrol-0.12.6/tox.ini 2019-12-22 18:43:35.000000000 +0100
+++ new/cachecontrol-0.12.10/tox.ini 2021-11-05 18:07:09.000000000 +0100
@@ -1,5 +1,17 @@
+; SPDX-FileCopyrightText: 2015 Eric Larson
+;
+; SPDX-License-Identifier: Apache-2.0
+
[tox]
-envlist = py27, py34, py35, py36, py37
+envlist = py27, py36, py37, py38, py39
+
+[gh-actions]
+python =
+ 2.7: py27
+ 3.6: py36
+ 3.7: py37
+ 3.8: py38
+ 3.9: py39
[testenv]
deps = pytest