056. Memcached 入门

1. Memcached 简介


  • 是一个免费开源的、高性能的、具有分布式内存对象的缓存系统,它通过减轻数据库负载加速动态 Web 应用。
  • 本质上就是一个内存 key-value 缓存。
  • 协议简单,使用的是基于文本行的协议。
  • 不支持数据的持久化,服务器关闭之后数据全部丢失。
  • Memcached 简洁而强大,便于快速开发,上手较为容易。
  • 没有安全机制。

2. Memcached 设计理念


  • 简单的键/值存储。
    • 服务器不关心您的数据是什么样的,只管数据存储。
  • 服务端功能简单,很多逻辑依赖客户端实现。
    • 客户端专注如何选择读取或写入的服务器,以及无法联系服务器时要执行的操作。
    • 服务端专注如何存储和管理合适清除或重用内存。
  • Memcached 实例之间没有通信机制。
  • 每个命令的复杂度为 O(1)。
    • 慢速机器上的查询应该在 1ms 一下运行。高端服务器的吞吐量可以达到每秒数百万。
  • 缓存自动清除机制。
  • 缓存失效机制。

3. 安装和测试


yum install libevent-devel
wget https://memcached.org/latest
mv latest memcached-1.6.6.tar.gz
tar -zxf memcached-1.6.6.tar.gz
cd memcached-1.6.6
./configure --prefix=/usr/local/memcached
make && sudo make install

# 启动并使用 memcached
cd /usr/local/memcached
./bin/memcached -m 64 -p 11211 -u root -vvv
# 使用 memcached
# telnet memcached_server_ip port
telnet localhost 11211
常用启动参数
参数说明
-p <num>监听的 TCP 端口(默认:11211)
-U <num>监听的 UDP 端口(默认:11211,0 表示不监听)
-l <ip_addr>监听的 IP 地址(默认:INADDR_ANY,所有地址)
-d作为守护进程来运行
-u <username>设定进程所属用户(仅 root 用户可以使用)
-m <num>所有 slab class 可用内存的上限(默认:64MB)
-v提示信息(在事件循环中打印错误/警告信息)
-vv详细信息(还打印客户端命令/响应)
-vvv超详细信息(还打印内部状态的变化)

4. 常用命令


数据处理命令
分组命令描述
存储命令set用于将 value 存储在指定的 key 中。key 已经存在,更新该 key 所对应的原来的数据。
存储命令add用于将 value 存储在指定的 key 中,存在则不更新。
存储命令replace替换已经存在的 key 的 value,不存在,则替换失败。
存储命令append命令用于向已存在的 key 的 value 后面追加数据。
存储命令prepend向已存在 key 的value 的千面追加数据。
存储命令cas比较和替换,比对后,没有被其他客户端修改的情况下才能写入。
检索命令get获取存储在 key 中的 value,不存在,则返回空。
检索命令gets获取带有 CAS 令牌存的 value,若 key 不存在,则返回为空。
删除delete删除已存在的 key。
计算incr/decr对已存在的 key 的数字值进行自增或自减操作。
清除flush_all清除所有内容。
监控命令
命令描述
stats返回 memcached 的统计信息
stats settings正在运行的 memcached 的设置
stats items每个 slab class 的存储信息
stats sizes存储在缓存中的所有 item 的常规大小和计数
stats sizes_enable启动直方图的形式展示 sizes 信息
stats sizes_disable禁用直方图
stats slabs已激活的 slab 的信息
stats conns连接信息
stats reset清空统计数据

5. 客户端使用


  • Java 客户端(xmemcached)示例:

    MemcachedClient client = new XMemcachedClient("host", 11211);
    
    // 同步存储 value 到 memcached,缓存超时为 1 小时,3600 秒。
    client.set("key", 3600, someObject);
    // 从 memcached 获取 key 对应的 value。
    Object someObject = client.get("key");
    
    // 从 memcached 获取 key 对应的 value,操作超时 2 秒。
    someObject = client.get("key", 2000);
    // 更新缓存的超时时间为 10 秒。
    boolean success = client.touch("key", 10);
    
    // 删除 value
    client.delete("key");
    
  • 客户端支持的特性:集群下多服务器选择、节点权重配置、失败/故障转移、数据压缩、连接管理。

6. Java 使用 xmemcached 具体例子


1. 添加依赖
<dependency>
    <groupId>com.googlecode.xmemcached</groupId>
    <artifactId>xmemcached</artifactId>
    <version>xxx</version>
</dependency>
2. 配置类 AppConfig
@Configuration
@Profile("single")
public class AppConfig {

    @Bean
    public MemcachedClient memcachedClient() throws IOException {
        return new XMemcachedClient("127.0.0.1", 11211);
    }

}
3. 业务模拟 UserService
@Service
@Profile("single")
public class UserService {
    @Resource
    private MemcachedClient memcachedClient;

    public User findUser(String userId) throws Exception {
        User user;

        // 1. 判断缓存中是否存在
        user = memcachedClient.get(userId);
        if (user != null) {
            System.out.println("从缓存中读取到值:" + user);
            return user;
        }

        // TODO 2. 不存在则读取数据库或者其他地方的值
        user = new User(userId, "张三");
        System.out.println("从数据库中读取到值:" + user);
        // 3. 同步存储 value 到 memcached,缓存超时为 1 小时,3600 秒
        memcachedClient.set(userId, 3600, user);
        return user;
    }
}
4. 测试类
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration("classpath:applicationContext.xml")
@ActiveProfiles("single")
public class UserServiceTests {
    @Resource
    private UserService userService;

    @Test
    public void setTest() throws Exception {
        User user = userService.findUser("zp");
        System.out.println(user);
    }
}
5. 结果
  • 第一次运行,可以看到第一次因缓存中没有,从数据库读取。
  • 第二次运行,可以看到从缓存中读取。

7. 服务端配置


  • 命令行参数
    • 查看 memcached -hman memcached 获取最新文档。
  • init 脚本
    • 如果通过 yum 应用商店安装,可以使用 /etc/sysconfig/memcached 文件进行参数配置。
  • 检查运行配置
    • stats settings 查看运行中的 memcached 的配置(可以用 telnet 连接 memcached 进行测试)。

8. Memcached 性能


  • Memcached 性能的关键是硬件,内部实现是 hash 表,读写操作都是 O(1)。硬件好,几百万的 QPS 都是没问题的。
  • 最大连接数限制:内部基于事件机制(类似于 JAVA NIO)所以这个限制和 nio 类似,只要内存、操作系统参数进行调整,轻松几十万。
  • 集群节点数量限制:理论是没限制的,但是节点越多,客户端需要建立的连接就会越多。如果要存储的数据很多,优先考虑可以增加内存,成本太高的情况下,再增加节点。
  • memcached 服务端没有分布式的功能,所以不论是集群还是主从备份,都需要第三方产品支持。

9. 服务器硬件需要


  • CPU 要求
    • CPU 占用率低,默认为 4 个工作线程。
  • 内存要求
    • memcached 内容存在内存里面,所以内存使用率高。
    • 建议 memcached 实例独占服务器,而不是混用。
    • 建议每个 memcached 实例内存大小都是一致的,如果不一致则需要进行权重调整。
  • 网络要求
    • 根据用户传输的内容来定,网络越大越好,虽然通常 10M 就够用了。
    • 建议:项目往 memcached 传输的内容保持尽可能的小。

这些应该在前期规划的时候尽量考虑进去。

10. Memcached 应用场景


  • 数据查询缓存:将数据库中的数据加载到 memcached,提供程序的访问速度。
  • 计数器的场景:通过 incr / decr 命令实现评论数量、点击数统计、操作次数等等场景。
  • 乐观锁实现:例如计划任务多实例部署的场景下,通过 CAS 实现不重复执行。
  • 防止重复处理:CAS 命令。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值