如何配置Cartopy使其WMTS请求使用本地缓存?
解决Cartopy WMTS影像重复下载的缓存问题
Cartopy的add_wmts方法基于WMTSRasterSource实现,文档说明它支持重复请求的缓存机制,源码也显示会先检查本地缓存再发起请求。但实际结合Matplotlib绘制地图时,重复运行代码仍会产生网络流量、重复下载WMTS影像。用户调整地图非影像相关内容时,希望避免重复下载(防止被限流或封禁),且已设置cartopy.config['data_dir']为默认位置,该目录下已有SRTM高程数据、Natural Earth数据等缓存。示例代码如下:
import cartopy.crs as ccrs import matplotlib.pyplot as plt plt.figure() ax = plt.subplot(1,1,1,projection=ccrs.Mercator()) ax.set_extent([-122.55, -122, 37.4, 37.85], crs=ccrs.PlateCarree()) ax.add_wmts('https://basemap.nationalmap.gov/arcgis/rest/services/USGSImageryOnly/MapServer/WMTS/1.0.0/WMTSCapabilities.xml', layer_name='USGSImageryOnly') plt.show()
以下是让Cartopy正确使用本地缓存的几种方法:
- 检查WMTS缓存路径
Cartopy默认会把WMTS缓存存在cartopy.config['data_dir']/wmts目录下。先确认这个目录是否存在,首次运行代码后有没有生成对应图层的缓存文件。如果路径不对,可手动指定缓存目录:
import cartopy.config # 替换成你想要的缓存路径 cartopy.config['wmts_cache_dir'] = '/your/custom/cache/path/wmts'
- 强制跳过服务器缓存校验
有些WMTS服务器会返回缓存校验头(比如Cache-Control、ETag),导致Cartopy每次都去服务器验证缓存是否有效,进而重新下载。可以自定义下载器,强制优先使用本地缓存:
import os import cartopy.io.wmts from cartopy.io import Downloader class CachingWMTSDownloader(Downloader): def acquire_resource(self, target_path, request): # 本地文件存在就直接返回,不发起请求 if os.path.exists(target_path): return target_path # 文件不存在时再调用原方法下载 return super().acquire_resource(target_path, request) # 把自定义下载器注册给WMTSRasterSource cartopy.io.wmts.WMTSRasterSource.downloader = CachingWMTSDownloader()
把这段代码放在调用add_wmts之前,首次下载完成后,后续运行就会直接读取本地缓存。
确保请求参数完全一致
如果重复运行时地图的范围(extent)、投影(projection)或者缩放级别变了,Cartopy会请求新的瓦片,这属于正常情况。如果只是调整标注、线条这类非影像内容,一定要保证这些核心参数和第一次完全一致,才能命中缓存。手动预下载瓦片(适合固定场景)
要是上面的方法都不管用,可以先一次性把需要的瓦片下载到本地,然后搭建一个简易的本地WMTS服务指向这些文件。不过这种方法需要提前整理瓦片的存储结构,更适合固定区域的地图绘制场景。
内容的提问来源于stack exchange,提问作者Dan
相关产品推荐
相关产品推荐

