Флажок-кеш memoize параметры строки запроса URL-адреса также
Расширение флагового кэша имеет декодер @cache.memoize
для кэширования представления, включая представление *args
и **kwargs
. Однако некоторые из моих представлений также содержат строку запроса URL, например /foo/image?width=640
. Декоратор добавляет метод make_cache_key
к декорированной функции просмотра, которая может использоваться для настройки ключа кеша
Однако я не знаю, как получить request.args
вне контекста обычного запроса.
Любые идеи о том, как заставить @cache.memoize
работать с строками запроса URL-адреса?
Ответы
Ответ 1
У меня была такая же проблема сегодня, и я не нашел никакого примера в Интернете, поэтому немного поиграл.
Это моя make_cache_key:
def make_cache_key(*args, **kwargs):
path = request.path
args = str(hash(frozenset(request.args.items())))
lang = get_locale()
return (path + args + lang).encode('utf-8')
Вы можете использовать request.url вместо пути и хэшированных аргументов. Мне также нужно было добавить язык пользователя к ключу.
Кэширование представления:
@app.route("/test")
@cache.cached(timeout=50)
def test():
a = request.args.get('a')
b = request.args.get('b')
return a + b
test.make_cache_key = make_cache_key
Это работает, но я думаю, что это довольно громоздко. Оказалось, что key_prefix может быть вызываемым, который генерирует всю cache_key. Поэтому мы можем это сделать:
@app.route("/test2")
@cache.cached(timeout=50, key_prefix=make_cache_key)
def test2():
a = request.args.get('a')
b = request.args.get('b')
return a + b
Я только что придумал это и еще не использовал его в производстве, поэтому он может не работать во всех случаях.
Ответ 2
Начиная с версии 0.3.4, key_prefix может быть вызываемым:
Новое в версии 0.3.4: Может быть необязательно вызываемым, которое не принимает аргументов, но возвращает строку, которая будет использоваться как cache_key.
Вот документ: Flask-Cache
Ответ 3
благодаря Smoe и Asdine El Hrychy, вот моя версия; он генерирует ключ для текущей строки URL + запроса (которая, на мой взгляд, должна быть общей потребностью).
Примечание:
- строка запроса сортируется в попытке остаться неизменной, если вы запрашиваете
?a=foo&b=bar
или ?b=bar&a=foo
(изначально я сделал (k, v) for k, val in flask.request.args.viewitems() for v in sorted(val)
, но я изменил, чтобы отсортировать ключи тоже)
- он поддерживает тот же ключ с несколькими вхождениями, то есть:
?a=foo&a=bar
(и вернет тот же ключ, что и ?a=bar&a=foo
)
-
key_prefix
аргумент предназначен только для cached
, а не для memoize
, по крайней мере, с Flask-Cache 0.13.1, и поскольку он принимает URL-путь, он должен соответствовать большинству memoize
прецедентов
Код:
import flask
import urllib
def cache_key():
args = flask.request.args
key = flask.request.path + '?' + urllib.urlencode([
(k, v) for k in sorted(args) for v in sorted(args.getlist(k))
])
return key
# ...
import time
@app.route('/test')
@cache.cached(timeout=600, key_prefix=cache_key)
def test():
return time.time()
@app.route('/<value>/test')
@cache.cached(timeout=3600, key_prefix=cache_key)
def value_test(value):
return flask.jsonify(time=time.time(), value=value)
Ответ 4
Вы можете использовать flask-caching
:
Продолжение расширения флагов-кешей
С помощью чего вы можете сделать что-то вроде этого:
@app.route("/")
@cache.cached(timeout=10, query_string=True)
def index():
return render_template('index.html')
Документы из исходный код:
:param query_string: Default False. When True, the cache key
used will be the result of hashing the
ordered query string parameters. This
avoids creating different caches for
the same query just because the parameters
were passed in a different order. See
_make_cache_key_query_string() for more
details.
Ответ 5
так как я не хочу, чтобы брат сам делал больше работы, как цитирует аргументы, но следующий код может работать и может удовлетворить мое требование:
from flask import request
def cache_key():
return request.url
@main.route("/test/", methods=['GET'])
@cache.cached(timeout=10, key_prefix=cache_key)
def do_somthing():
return "hello %s" % str(request.args)