分布式系统缓存设计浅析

1. 分布式缓存面临比较大的三个问题:

(1) 数据一致性。

在分布式系统这点显得尤为重要,主要原因有三点:

缓存系统与底层数据的一致性。这点在底层系统是“可读可写”时,写得尤为重要

有继承关系的缓存之间的一致性。为了尽量提高缓存命中率,缓存也是分层:全局缓存,二级缓存。他们是存在继承关系的。全局缓存可以有二级缓存来组成。

多个缓存副本之间的一致性。为了保证系统的高可用性,缓存系统背后往往会接两套存储系统(如memcache,redis等),以上的ppt也主要是讲这方面的内容。

(2)缓存雪崩

当缓存系统重启或者所有缓存在同一时刻失效(比如某些系统为了提高速度,会在系统启动是统一将大部分数据刷到缓存中,此时如果设置缓存时间都是24小时,那24小时过后,那就悲剧)时,应用系统由于扛不住压力而直接挂掉。

(3)缓存穿透

查询一个必然不存在的数据,查询一个必然不存在的key,每次都会访问DB,如果有人恶意破坏,那么很可能直接对DB造成影响。

第一点偏重数据的真实性和实时性,而第二点和第三点更多从性能上考虑。同时缓存并不一定是必需的,特别是当写操作特别频繁时。

2. 缓存数据的淘汰

原先缓存数据的淘汰往往是用设置缓存时间,比如我设置某个数据的缓存时间是24小时,之后的24内这个缓存是不会失效的。优点当然是简单,缺点也很明显就是不都灵活,没做到好的精细化管理。

我们能利用的资源就是:1. 给缓存加tag,2. 版本号(必须单调递增,时间戳是最好的选择)3. 提供手动清理缓存的接口。

相关步骤可以参见以上的PPT内容。

缓存相关接口:

var me = Cache.create(...);
me.set(key, value, ttl, tags);
me.get(key);
me.tagrm(tag, offset, flush);

缓存的数据结构如下:

var data = {
  ‘i’:now, /** 数据写入时间戳 */
  ‘e’:now + ttl,/** 预期过期时间 */
  ‘k’:key, /** 原始key */
  ‘v’:value, /** 原始值 */
  ‘t’:tags /** tag列表 */
};

我刚开始的也没弄明白为什么在data中还要存“原始的key”,后来经朋春提醒,才弄明白:原始的key可能过长或者存在特殊字符时,是不能直接作为某些系统的key,因此往往会对原始key做一次hash来作为缓存的新key。

3. 缓存淘汰的策略

缓存淘汰的策略有两种:

(1) 定时去清理过期的缓存。

(2)当有用户请求过来时,再判断这个请求所用到的缓存是否过期,过期的话就去底层系统得到新数据并更新缓存。

两者各有优劣,第一种的缺点是维护大量缓存的key是比较麻烦的,第二种的缺点就是每次用户请求过来都要判断缓存失效,逻辑相对比较复杂,具体用哪种方案,大家可以根据自己的应用场景来权衡。

原文:分布式系统缓存设计浅析

时间: 2024-10-13 11:59:07

分布式系统缓存设计浅析的相关文章

H5缓存机制浅析-移动端Web加载性能优化【干货】

转载:H5缓存机制浅析-移动端Web加载性能优化[干货] 作者:贺辉超,腾讯游戏平台与社区产品部 高级工程师 目录 1 H5缓存机制介绍 2 H5缓存机制原理分析 2.1 浏览器缓存机制 2.2 Dom Storgage(Web Storage)存储机制 2.3 Web SQL Database存储机制 2.4 Application Cache(AppCache)机制 2.5 Indexed Database (IndexedDB) 2.6 File System API 3 移动端Web加载

【转】缓存设计的一些思考

***{转自:缓存设计的一些思考}*** 互联网架构中缓存无处不在,某厂牛人曾经说过:”缓存就像清凉油,哪里不舒服,抹一下就好了”.高品质的存储容量小,价格高:低品质存储容量大,价格低,缓存的目的就在于”扩充”高品质存储的容量.本文探讨缓存相关的一些问题. LRU替换算法 缓存的技术点包括内存管理和替换算法.LRU是使用最多的替换算法,每次淘汰最久没有使用的元素.LRU缓存实现分为两个部分:Hash表和LRU链表,Hash表用于查找缓存中的元素,LRU链表用于淘汰.内存常以Slab的方式管理.

21、缓存设计

? 什么是缓存 缓存一般是磁盘或内存中的存储区域,用于存储从网络或其他数据源 获取的文件.通常这些数据源的访问速度远低于缓存的访问速度.使用 缓存可以大大提高程序的运行效率,但数据不会实时更新. ? 缓存设计原理  这里以ListView为例.在ListView上显示多个从网络上下载的图片. 如果是第一次运行程序,需要实时从网络上下载这些图片文件.但由于 网络速度的原因,如果一边下载.一边显示,ListView就会有些卡.所以 我们采用了缓存技术,也就是说,当ListView显示网络上某个图片时

由Android缓存设计想到的

由Android缓存设计想到的 前言 Android这种对内存比较敏感的系统,在处理大量图片的时候不可避免要用到缓存,那么到底是应该使用虚拟机底层通过GC回收保障的SoftReference,还是使用一个带LRU算法的队列,哪个更适合Android系统下的应用? 基本概念 缓存,顾名思义把已经读取到的数据存下来,供再次读取,合理的使用缓存可以减少一些昂贵代价的动作(数据库操作,文件读写,网络传输,等),缓解系统压力,提高程序响应速度. 设计缓存需要注意的几个方面:缓存的容量,如何使缓存维持在一个

百万级运维经验五:网站缓存设计

大访问量的网站少不了缓存,那如何设计网站的缓存呢? 网站缓存可以有很多种: 1.根据数据表和主键缓存单条数据,如每个用户,每篇文章等等. 2.缓存数据列表,通常用于显示多条数据的地方.如缓存前200篇文章,因为一般前200条数据的查询次数是最多的. 3.缓存模板块,比如某个页面,其中一部分的内容是很少变动的,可以把这部分内容缓存起来. 4.缓存整个页面,比如首页,当程序生成整个页面的内容时,把内容缓存起来,下次访问时直接从缓存里取. 5.数据统计缓存,如评论数.收藏数等. 目前我所了解的是这4钟

CYQ.Data V5 分布式自动化缓存设计介绍(二)

前言: 最近一段时间,开始了<IT连>创业,所以精力和写的文章多数是在分享创业的过程. 而关于本人三大框架CYQ.Data.Aries.Taurus.MVC的相关文章,基本都很少写了. 但框架的维护升级,还是时不时的在进行中的,这点从开源的Github上的代码提交时间上就可以看出来了. 毕竟<IT连>的后台WebAPI,用的是Taurus.MVC,后台系统管理用的是Aries. 不过今天,就不写创业相关的文章了,先分享篇技术类的文章. CYQ.Data 分布式自动缓存 之前写过一篇

nginx+Memcached 缓存设计

单页面缓存方案 单静态页缓存 解决问题场景 常见的缓存设计利用System.Web.Cache 保存在内存内,效率高,可以减轻数据库访问的压力.但是Web除了获取数据之外,还有呈现页面渲染,生成HTML很多功能都是消耗性能.在Web层也需要一个缓存,同时柔性设计,应用代码不需要大变动. 架构 客户端 访问 /Report Nginx 接收请求,判断Memcached是否存在以该网址的Key,存在直接返回不经过IIS,不存在 ,透传到IIS,并在Memacched中保存 优势:memcached性

本地缓存设计

被问到本地缓存设计,有点蒙,事后反应过来,何必一个Map呢,两个就可以解决了.真是当时脑子短路了. package cache; import java.util.Map;import java.util.concurrent.ConcurrentHashMap; public class MyCache<K, V> { private static class ValueObject<T> { private T value; private long timeout; priv

MyBatis缓存设计

和大多数ORM框架一样,为了尽可能减少数据库的访问,MyBatis设计支持缓存功能.设计上通过Cache接口提供SPI(服务提供接口),可以让第三方缓存提供具体的缓存实现,比如使用ehcache.Redis等,通过这些常用环境提供的实现类,即可将其配置成MyBatis中使用的缓存. 除了给第三方缓存提供SPI接口外,MyBatis自身也通过HashMap做了简单的缓存实现.总体上MyBatis缓存设计分为一级缓存和二级缓存. MyBatis一级缓存是SqlSession级别的本地缓存,默认开启不