Skip to content

Instantly share code, notes, and snippets.

@mauler
Last active September 18, 2019 10:26
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save mauler/7d8d80984311bab2f8831185de70f1af to your computer and use it in GitHub Desktop.
Save mauler/7d8d80984311bab2f8831185de70f1af to your computer and use it in GitHub Desktop.
functool lru_cache with timeout allowing to set expiration time on cached values
import datetime
from functools import lru_cache, wraps
def lru_cache_timeout(timeout_seconds: int):
def decorator(f):
@lru_cache(maxsize=None)
def f_cache_id(f_cache_id, *args, **kwds):
return f(*args, **kwds)
@wraps(f)
def decorated(*args, **kwds):
cache_id = int(datetime.datetime.now().timestamp() / timeout_seconds)
return f_cache_id(cache_id, *args, **kwds)
return decorated
return decorator
if __name__ == '__main__':
TIMEOUT_SECONDS = 2
# get_database_connection() is an example usage
conn_id = 0
@lru_cache_timeout(timeout_seconds=TIMEOUT_SECONDS)
def get_database_connection():
global conn_id
conn_id += 1
print('Created new database connection ID: {}'.format(conn_id))
return conn_id
# Retrieve 3 times on the same time, should be the same connection id
assert get_database_connection() == 1
assert get_database_connection() == 1
assert get_database_connection() == 1
# Sleep to make sure the timeout is gone:
import time
time.sleep(TIMEOUT_SECONDS)
# Connection changed, but still cached
assert get_database_connection() == 2
assert get_database_connection() == 2
assert get_database_connection() == 2
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment