Docker启动Redis及Redis内存模型讲解
"Cmd": [ "redis-server", "/usr/local/etc/redis.conf" ] ...... "WorkingDir": "/data",
看到docker中redis启动时使用的命令redis-server /usr/local/etc/redis.conf,redis.conf中dir配置的数据存储位置为./,即当前目录,docker上工作目录为/data,所以redis数据存储目录为/data。
有的docker inspect中没有redis.conf;可以在启动docker容器时候指定。
2. 注意数据存储路径为目录,本地创建目录/root/redis/data,本地redis.conf存放在/root/redis文件夹下,使用docker启动docker reids命令如下
docker run --name myredis -p 6379:6379 -v /root/redis:/usr/local/etc -v /root/redis/data:/data -d redis
redis.conf文件内容可到https://www.cnblogs.com/hujiapeng/p/16413404.html复制出来
docker中端口映射使用-p,如果是-P的话,主机会随机分配一个端口。
如下可以通过redis-server指定redis.conf路径。
docker run --name myredis -p 6379:6379 -v /root/redis/conf:/usr/local/etc -v /root/redis/data:/data -d redis redis-server /usr/local/etc/redis.conf
注意,如果修改redis.conf文件,daemonize配置为no,默认就为no;注释掉bind 127.0.0.1;没有设置密码的话,配置protected-mode no。
docker logs myredis可以查看已启动信息
3. 启动如果报错chown: changing ownership of '.': Permission denied,需要关闭selinux
- 暂时关闭selinux: setenforce 0
- 查看状态命令: getenforce , Enforcing表示没关闭, Permissive 表示已关闭
- 永久关闭:编辑/etc/sysconfig/selinux,设置SELINUX=disabled
4. 对于是否关闭虚拟内存,我觉得不应该关闭,有的认为开启后如果内存不够会影响性能,但是如果关闭内存不够后系统就会直接停到redis进程
关闭所有虚拟内存命令:swapoff -a,开启所有虚拟内存命令:swapon -a。通过free -m命令可以查看Swap是否开启或大小。对于如何创建虚拟内存或配置虚拟内存自行补充吧
5. 进入docker redis命令:docker exec -it myredis /bin/bash
6. 启动reids客户端连接redis命令:redis-cli
7. info memory命令查看内存清空
- used_memory表示已使用内存大小,_human表示的可读性好
- used_memory_rss表示redis进程使用的内存大小,_human表示的可读性好,包含了进程启动本身所需和存储的数据大小
- mem_fragmentation_ratio表示碎片比例,=used_memory_rss/used_memory,正常情况这个值是趋向于1的,如果大于1太多,如是1.5表示50%碎片率,redis内存管理器会根据碎片整理策略进行整理内存碎片,如果小于1,表示使用了虚拟内存,redis性能会降低。
- mem_allocator表示内存分配器
8. Redis碎片整理功能默认关闭,可通过配置activedefrag进行开启,以及配置碎片整理策略,文档中有说明,如果不需要进行碎片整理就不要开启,内存分配器后台任务会自动整理,如果需要开启也建议通过命令来开启
9. Redis数据是以Key、Value对形式的哈希字典方式存储,每一个键值对的数据结构就是一个dictEntry,包含一个SDS类型的Key、redisObject类型的Value和指向下一个dictEntry的指针next
- SDS表示为动态字符串,用来存储字符串类型的数据
- redisObject数据结构包含代表Value对象类型的type、指向Value存储地址的ptr指针、所存储数据的编码等
- Redis中常用的五种数据类型,String、List、Set、Sorted Set(zset)、Hash,如果想看存储数据的数据类型可以使用命令type key
10. 如果想看存储数据的编码,使用命令object encoding key
- string有三种编码方式:值为整型时用int、字节数小于等于44时用embstr、字节数大于44时用raw
- list有两种:双向链表和压缩列表,其实3.2版本后为了减少linkedList和zipList的转换,使用了quickList来存储数据。quicklist其实就是linkedlist和ziplist的结合,quicklist中的数据先用quicklistnode存储ziplist,当达到限定ziplist数量后,再追加一个quicklistnode继续操作
- hash有两种:压缩列表和哈希表
- sorted set有两种:压缩列表和跳表
- set有两种:整数数组和哈希表
11. Redis补充类型
- bitmap,二进制形式数组(0-2^32,最大512M):setbit key offset value
- hyperloglog,基数统计:pfadd key val [val...];pfcount key;
- geospatial,地理位置(本质上基于Sorted Set,所以可以使用zset一些命令):geoadd,geodist,geopos等等
12. 对于key value对,如果能用整型作为value就用整型,这样可以利用到redis的共享对象特点
13. Redis4.0新增惰性删除或延迟删除特性,就是开启异步延迟删除数据功能(配置文件中以lazyfree-开头的几个),减少对Redis主线程的阻塞,如果对数据一致性要求高建议比较key的过期时间
14. 缓存淘汰策略,经常使用volatile-lru:淘汰所有设置了过期时间的键值中最久未使用的。Redis默认使用noeviction,不淘汰任何数据,当内存不足时新增会报错
- LRU,最近最少使用
- LFU,最近最少频次被访问的
15. Jedis访问Demo
mave引入
<dependencies> <dependency> <groupId>redis.clients</groupId> <artifactId>jedis</artifactId> <version>2.8.1</version> </dependency> </dependencies>
Java代码
public static void main(String[] args) { Jedis jedis = new Jedis("192.168.1.4", 6379); jedis.set("a", "1"); String value = jedis.get("a"); jedis.close(); System.out.println(); }