pythonsqlalchemytransactionspyramidbeaker

How can one combine pyramid_beaker decorator-style caching and pyramid_tm?


With Pyramid / pyramid_tm I end up passing around the dbsession object that joined the current transaction to methods that encapsulate my code. For example

def get_item_name(dbsession, item_id):
    item = dbsession.query(...)
    return item.name

def view_func(request):
    item_name = get_item_name(request.dbsession, request.GET['item_id']
    ...

Now if I wanted to cache the results of get_item_name using the beaker cache decorator @cache_region for example, I would never get a cache hit since dbsession is part of the cache key.

What is a common pattern to solve this elegantly?


Solution

  • At least one pattern is to decorate a closure that only accepts the args you want to cache and accesses other variables like request/dbsession from nonlocal scope.

    def view_func(request):
        @cache.region('short_term')
        def get_item_name(item_id):
            item = request.dbsession.query(...)
            return item.name
        item_name = get_item_name(request.GET['item_id'])
    

    This pattern is common in the beaker docs.