diff --git a/.flake8 b/.flake8 new file mode 100644 index 0000000..1fd4893 --- /dev/null +++ b/.flake8 @@ -0,0 +1,2 @@ +[flake8] +max-line-length = 160 diff --git a/.travis.yml b/.travis.yml index e576121..a4943ea 100644 --- a/.travis.yml +++ b/.travis.yml @@ -6,4 +6,6 @@ python: install: - pip install -r requirements-dev.txt - pip install . -script: pytest +script: + - pytest + - flake8 diff --git a/fcache/__init__.py b/fcache/__init__.py index e66d264..dfff241 100644 --- a/fcache/__init__.py +++ b/fcache/__init__.py @@ -1 +1,3 @@ from .fcache import fcache + +__all__ = ["fcache"] diff --git a/fcache/fcache.py b/fcache/fcache.py index aa07ff5..0e8a213 100644 --- a/fcache/fcache.py +++ b/fcache/fcache.py @@ -8,10 +8,12 @@ GLOBAL_CACHE = FileCache('.fcache') + def get_global_cache(): global GLOBAL_CACHE return GLOBAL_CACHE + def get_func_fullname(f, bounded_obj): f_name = getattr(f, '__module__', '') + '.' if bounded_obj is not None: @@ -21,6 +23,7 @@ def get_func_fullname(f, bounded_obj): def fcache(f): cache = get_global_cache() + def decorated(*args, **kwargs): if f.__closure__: f_closure_values = tuple(map(lambda c: c.cell_contents, f.__closure__)) @@ -38,8 +41,12 @@ def decorated(*args, **kwargs): cache[call_hash] = ret_val return ret_val return decorated + + +# XXX replace fcache by a object fcache.clear_at_exit = False + @atexit.register def maybe_clear_at_exit(): if fcache.clear_at_exit: diff --git a/fcache/file_cache.py b/fcache/file_cache.py index ca26935..2bde484 100644 --- a/fcache/file_cache.py +++ b/fcache/file_cache.py @@ -9,11 +9,13 @@ def __init__(self, prev, next, key): self.next = next self.key = key + # TODO use slots class LruList: def __init__(self, next): self.next = next + class FileCache: def __init__(self, cache_dir, capacity=80*1024*1024*1024): self._cache_dir = cache_dir @@ -27,7 +29,8 @@ def __init__(self, cache_dir, capacity=80*1024*1024*1024): disk_files = [] for cached_pickle in os.listdir(cache_dir): key, ext = os.path.splitext(cached_pickle) - if ext != '.pkl': continue + if ext != '.pkl': + continue key = int(key) full_fn = os.path.join(cache_dir, cached_pickle) disk_files.append((full_fn, os.stat(full_fn), key)) @@ -75,7 +78,7 @@ def __contains__(self, key): def pop_lru(self): lru = self._lru_items.next - #del self[lru.key] + # del self[lru.key] del self._cached_keys[lru.key] size = os.stat(self.cache_fn(lru.key)).st_size os.unlink(self.cache_fn(lru.key)) diff --git a/fcache/hashing.py b/fcache/hashing.py index 8562d45..bbe1840 100644 --- a/fcache/hashing.py +++ b/fcache/hashing.py @@ -1,7 +1,6 @@ import hashlib import pickle import io -from collections import OrderedDict class StablePickler(pickle.Pickler): diff --git a/fcache/tests/test_caching_functions.py b/fcache/tests/test_caching_functions.py index 8fb948c..415fed7 100644 --- a/fcache/tests/test_caching_functions.py +++ b/fcache/tests/test_caching_functions.py @@ -2,6 +2,7 @@ fcache.clear_at_exit = True + class Num: def __init__(self, n): self.n = n @@ -16,14 +17,18 @@ def __iadd__(self, other): self.n += other.n return self + # Test global function global_function_call_counter = 0 + + def global_function(n): global global_function_call_counter global_function_call_counter += 1 return n * n + def test_global_function(): cached = fcache(global_function) exp_5 = global_function(5) @@ -54,7 +59,7 @@ def loc_func(n): # Test lambda def test_lambda(): - lamb = lambda x: x + lamb = lambda x: x # NOQA cached = fcache(lamb) for i in range(5): for n in range(5): @@ -67,6 +72,7 @@ def test_lambda(): else: assert f_input is not cached_res + # Test redifining a function def test_redefining_a_function(): @fcache @@ -94,13 +100,16 @@ def fun(n, add=1): # Test closure def test_closure(): + def outer(): n = Num(0) + @fcache def mut(): nonlocal n n += Num(1) return n + @fcache def get(): return n @@ -112,7 +121,7 @@ def get(): assert mut() == Num(3) get_res = get() cached_res = get() - assert get_res == Num(3) + assert get_res == Num(3) assert cached_res == get_res assert cached_res is not get_res @@ -121,11 +130,14 @@ def get(): class SimpleClass: def __init__(self): self.n = 0 + def inc(self): self.n += 1 + def get(self): return self.n + def test_bound_method(): obj = SimpleClass() fun = fcache(obj.get) diff --git a/fcache/tests/test_file_cache.py b/fcache/tests/test_file_cache.py index 455b8ac..d9993df 100644 --- a/fcache/tests/test_file_cache.py +++ b/fcache/tests/test_file_cache.py @@ -1,5 +1,6 @@ from fcache.file_cache import FileCache + def test_caching_values(tmpdir): cache = FileCache(str(tmpdir)) kvs = [(1, 1), (2, 20), (3, 300)] @@ -28,6 +29,7 @@ def test_cache_clearing(tmpdir): cache.clear() assert len(cache) == 0 + def test_cache_limit(tmpdir): record_size = 512 cache = FileCache(str(tmpdir), capacity=int(2.5*record_size)) @@ -45,6 +47,7 @@ def test_cache_limit(tmpdir): assert 1 in cache assert 3 in cache + def test_cache_limit_restore_from_disk(tmpdir): record_size = 512 cache = FileCache(str(tmpdir), capacity=int(2.5*record_size)) diff --git a/fcache/tests/test_hashing.py b/fcache/tests/test_hashing.py index de040b1..b143f29 100644 --- a/fcache/tests/test_hashing.py +++ b/fcache/tests/test_hashing.py @@ -15,8 +15,8 @@ def get_hash(repr_): env = os.environ cmd_line = [sys.executable, '-c', get_hash_command(repr_)] p = subprocess.Popen(cmd_line, stdin=subprocess.PIPE, - stdout=subprocess.PIPE, stderr=subprocess.STDOUT, - env=env) + stdout=subprocess.PIPE, stderr=subprocess.STDOUT, + env=env) out, err = p.communicate() return int(out.strip()) diff --git a/requirements-dev.txt b/requirements-dev.txt index eaeed47..3061c78 100644 --- a/requirements-dev.txt +++ b/requirements-dev.txt @@ -1 +1,2 @@ pytest==3.0.5 +flake8 diff --git a/setup.py b/setup.py index 1e02ce8..6c1d4c7 100644 --- a/setup.py +++ b/setup.py @@ -10,4 +10,3 @@ install_requires=[ ], ) -