Кэширование ответа на запрос в python
Я пишу несколько бэкэнд-скриптов на python, которые должны быть связаны с веб-интерфейсом, использующим django.
Веб-приложение позволяет просматривать слои, поступающие из различных веб-сервисов. В рамках своих задач я разработал инструмент, который запрашивает данные о высоте с геосервера (сервис WCS), а затем, основываясь на предыдущей линии, нарисованной пользователем во фронт-энде, может генерировать поперечный срез базовых данных.
Короче говоря, когда пользователь проводит линию по слою, а затем нажимает кнопку draw-profile, моя функция запрашивает данные, пересекает линию по связанному растру/слою и возвращает рисунок на фронт-енд.
Проблема такого подхода заключается в том, что каждый раз, когда пользователь нажимает кнопку draw-profile, запрос выполняется заново, что занимает некоторое время.
Когда запрос выполнен, данные сохраняются в DTM object
(класс, который я сделал) в self.raster
свойстве.
Упрощенная версия функции, запрашивающей данные, показана ниже.
def get_dtm_from_wcs100(
self,
raster_source: str = "YY",
layer: str = "XX",
format: str = "image/tiff",
version: str = "1.0.0",
resx: int = 1,
resy: int = 1,
) -> None:
"""
Get raster and metadata from a WCS service
Parameters
----------
raster_source : str, optional
URL of WCS service. The default is "YY" which is the company geoserver
layer : str, optional
CoverageID. The default is 'XX'.
format : str, optional
File type of the request. The default is 'image/tiff'.
version : str, optional
Version of the WCS protocol. The default is "1.0.0".
resx : int, optional
Pixel resolution in x-coordinate. The default is 1.
resy : int, optional
Pixel resolution in y-coordinate. The default is 1.
Returns
-------
None.
"""
try:
# Connect to WCS and try getting a coverage
wcs = WebCoverageService(raster_source, version=version)
response = wcs.getCoverage(
identifier=layer,
bbox=self.bbox,
crs=self.epsg,
format=format,
resx=resx,
resy=resy,
)
except Exception as e:
raise Exception("An unexpected error has ocurred:", e)
else:
self._read_response(response)
self._set_masked_raster()
При выполнении self._read_response(response)
заполняется свойство self.raster
(numpy array
).
Знаете ли вы, что я могу сделать, чтобы как-то сохранить этот ответ и не вызывать его каждый раз, когда я хочу нарисовать профиль?
Вы можете использовать декоратор @cache
из питоновского functools
.
https://docs.python.org/3/library/functools.html
Можно использовать службу кэширования памяти, например Memcached, Redis и т. д., и привязать сессию пользователя к кэшированной версии ответа от WebCoverageService.
Вы также можете сериализовать ответ (сопоставив его с пользовательской сессией) и хранить его локально.
Ваш подход будет зависеть от среды, в которой вы запускаете эту службу. Если ваш сервис работает в классической инфраструктуре виртуальных машин, например Amazon EC2, то локальный файловый кэш будет работать. Однако если вы работаете в Kubernetes, вам действительно следует изучить Memcached, Redis и т. д.