Redis进阶操作
- Redis事务处理
Redis本身支持事务处理,但是这种支持的事务处理本身是存在设计缺陷的,而且与传统的关系型数据库的事务处理有些不同,首先先来看一下Redis中的事务支持命令:
1.打开事务:multi
2.取消事务:discard
3.提交事务:exec
范例:观察Redis中的事务:
设置一个数据:set age 30
打开事务支持:multi 执行完毕提示OK
(QUEUED)进行数据操作:set age 300
(QUEUED)进行数据操作:set age 3000
关闭事务:discard
操作完毕,age值仍然是30
一旦我们开启了Redis事务控制,则表示所有的更新操作都要追加到一个更新队列之中。
由于现在执行完更新之后,发现数据本身出现有问题了,所以选择关闭事务,一旦事务关闭之后那么该操作将会回滚到最初的状态。
执行事务的提交:
设置一个数据:set age 30
打开事务支持:multi 执行完毕提示OK
(QUEUED)进行数据操作:set age 50
提交事务:exec
如果在事务开启状态下进行了更新处理,随后只有执行了exec指令后才表示事务真正提交,才会真正影响到原始数据(有bug)
但是需要提醒的是,Redis设计之初就是不考虑事务的,所以以上的事务只能够说是Redis的一个玩笑。因为这种事务设计的并不完善
比如:
设置一个数据:set id mldn
打开事务支持:multi 执行完毕提示OK
(QUEUED)进行数据操作:incr id
(QUEUED)进行数据操作:set age 500
提交事务:exec
提交事务时会报错:
1)ERR value is not an integer or out of range
2)Ok
这个时候事务一旦提交会出现错误信息,因为id的数据不是数字,所以无法进行数字的增长,但是set age 500执行了,而且一旦出现了错误之后,其他的更新操作依然可以正常完成。
NoSql一般都不考虑事务的处理
- 乐观锁
在数据库执行操作的时候,为了保证数据的一致性,即A用户更新数据的时候B用户不能够更新。所谓的锁在数据库的设计上分为两种,一种叫悲观锁,一种叫乐观锁,
悲观锁:基于数据库的操作实现
select * from member where mid=1 for update;
一旦加上for update 该条数据无法更新
乐观锁:基于算法的实现,在我们的数据表上追加一个锁的处理列,
在每次提交前,都会进行锁编号的判断,一致则可以提交,不一致说明其他用户修改了此值,需要再次取值提交。
在Redis里边是直接支持乐观锁的,如果想要观察乐观锁的处理,则可以打开两个不同的session
1.【第一个session】执行如下的操作:
设置一个数据:set age 30
进行该数据的监听:watch age
启用事务:multi
这个时候并没有对age数据做任何修改;
2.【第二个session】执行如下的操作–对数据进行修改操作:
覆盖age数据:set age 500
取得age数据:get age
3.【第一个session】对数据进行修改
修改数据:set age 60
提交事务:exec
此时由于第二个session已经更新了原始的数据,那么就表示该原始数据上的一个标记列更新,这样当第一个session更新的时候会发现返回了‘nil’,意味着本次更新失败。
Redis最大的特征就是把标志位给隐含掉了,如果是关系型数据库则需要手动标记,然后再进行处理操作
- Redis密码配置
如果说你现在的redis没有进行认证的处理操作,那么所有的程序都可以进行连接,直接使用redis-cli命令只需要设置上主机名称和端口号就可以进行连接处理,那么为了安全必须要设置密码
在redis数据库设计的时候并没有像其他数据库那样准备了一堆复杂的密码或者权限的概念,在Redis里面只需要设置一个认证密码就可以解决问题了,没有所谓的用户名等问题
1.修改redis.conf配置文件
找到reuqirepass foobared
追加以下内容:
requirepass wanghaoxin
2.随后关闭redis服务并且重新启动:
关闭redis服务:killall redis-server
重新启动redis服务:/usr/local/redis/conf# /usr/local/redis/bin/redis-server /usr/local/redis/conf/redis.conf
3.登陆Redis服务器
/usr/local/redis/conf# /usr/local/redis/bin/redis-cli -h 127.0.0.1 -p 6379
–这个时候发现可以正常登陆Redis数据库,但是一旦执行数据操作,key * 等操作,就会出现(error) NOAUTH Authentication required错误信息。
–此时需要执行如下命令进行认证处理:
auth wanghaoxin
–或者直接在登陆的时候使用密码参数
/usr/local/redis/conf# /usr/local/redis/bin/redis-cli -h 127.0.0.1 -p 6379 -a wanghaoxin
所有的Redis服务一定要有认证密码,而且作为Redis集群开发设计的时候一定要将所有密码统一
- *Redis性能监控
Redis作为缓存数据库使用,那么一旦在开发之中使用了Redis数据库,就表示有可能会大面积的去向Redis里面保存数据(缓存的目的:不断的快速读取和写入)
那么现在如果要想知道当前的运行状态,那么就需要对其进行监控处理,如果要进行Redis监控,Redis本身没有提供,必须通过其他组件完成,本次使用一个”redis-stat”工具实现Redis监控操作,这个工具可以直接通过GitHub找到
redis-stat下载地址:
https://github.com/junegunn/redis-stat
1.为了更加清楚的发现redis-stat的特点,建立三个redis运行进行进程,模拟方法很简单,配置不同的redis端口即可,也就是说你需要准备出不同的redis.conf配置文件:
2.建立redis数据的保存目录,要求可以同时保存三个redis进程
进入到/usr/data目录下,
删除redis目录:rm -r redis/
运行:mkdir -p /usr/data/redis/{redis-6379,redis-6380,redis-6381}/{run,logs,dbcache}
3.将之前的redis.conf文件拷贝三份
cp /usr/local/redis/conf/redis.conf /usr/local/redis/conf/redis-6379.conf
cp /usr/local/redis/conf/redis.conf /usr/local/redis/conf/redis-6380.conf
cp /usr/local/redis/conf/redis.conf /usr/local/redis/conf/redis-6381.conf
4.编辑每一个配置文件,修改各自的内容,以redis-6379为例
取消外网访问的限制:#bind 127.0.0.1(不写意味着redis无法被外部java程序访问使用)
设置端口:port 6379
修改pid保存路径:pidfile /usr/data/redis/redis-6379/run/redis_6379.pid
修改log日志文件路径:logfile “/usr/data/redis/redis-6379/logs/redis.log”
修改数据文件日志目录:
dir /usr/data/redis/redis-6379/dbcache
同理:修改其它文件
或者可以采用复制替换:
1,$s/6379/6381/g
代表从第一行到最后 全局替换
6.启动所有的redis服务
/usr/local/redis/bin/redis-server /usr/local/redis/conf/redis-6379.conf
/usr/local/redis/bin/redis-server /usr/local/redis/conf/redis-6380.conf
/usr/local/redis/bin/redis-server /usr/local/redis/conf/redis-6381.conf
ps -ef|grep redis
netstat -nptl查看
本机redis三个进程全部有了
7.通过GitHub下载redis-stat开发包
如果要想使用redis-stat,必须下载ruby相关环境;
apt-get install ruby-dev rubygems;
将该工具下载到“/usr/local”目录之中:cd /usr/local/;
进行redis-stat的下载
git clone https://github.com/junegunn/redis-stat.git
8.下载下来的redis-stat里面实际只有一个执行命令
/usr/local/redis-stat/bin/redis-stat
必须进入到redis-stat所在的目录:
cd /usr/local/redis-stat/bin
如果要想使用这个命令,则必须使用ruby进行该命令的处理(否则不能使用):
gem install redis-stat
9.启动redis-stat工具进行监听控制:(-a wanghaoxin 为权限认证)
/usr/local/redis-stat/bin/redis-stat 192.168.231.128:6379 192.168.231.128:6380 192.168.231.128:6381 -a wanghaoxin
10.该工具还支持Web启动查看,也就是它内部自动提供有一个HttpServer:
/usr/local/redis-stat/bin# /usr/local/redis-stat/bin/redis-stat 192.168.231.128:6379 192.168.231.128:6380 192.168.231.128:6381 -a wanghaoxin –server –daemon –verbose
此时默认端口为63790
也可以:
/usr/local/redis-stat/bin# /usr/local/redis-stat/bin/redis-stat 192.168.231.128:6379 192.168.231.128:6380 192.168.231.128:6381 -a wanghaoxin –server=80 –daemon –verbose
表示80端口
( –verbose :表示展示更多信息,–server :Launch redis-stat web server (default port: 63790) –daemon :后台运行)
启动浏览器 ip:192.168.231.128:63790
http://192.168.231.128:63790
如果是80端口则直接输入:
http://192.168.231.128
11.使用redis提供的测试工具来做测试:
/usr/local/redis/bin/redis-benchmark -h 192.168.231.128 -p 6379 -a wanghaoxin -c 100 -d 10 -n 100
/usr/local/redis/bin/redis-benchmark -h 192.168.231.128 -p 6380 -a wanghaoxin -c 100 -d 10 -n 100
/usr/local/redis/bin/redis-benchmark -h 192.168.231.128 -p 6381 -a wanghaoxin -c 100 -d 10 -n 100
这样可以在浏览器中监控情况
可以根据监控情况可以及时调整服务器的硬件设施,也可以推算出用户的访问情况
- 使用java操作redis数据库
1.java连接redis数据库
Redis本身提供有一个java语言支持,(不仅仅支持java,各个语言都支持),这个组件为jedis组件,也就是说如果你要进行Redis的编程开发,就需要通过maven获取该组件:
打开mavenrepository:
http://mvnrepository.com/
查找jedis:
获取最新版本(最好匹配最新版本因为redis是最新版本)
1.新建一个jedis的Maven项目:
2.修改pom.xml配置文件,追加相应的开发包以及插件
3.如果要进行redis数据库的连接,千万不要做地址的绑定(斗则会不能使用 即把bind 127.0.0.1注释掉)
正常返回:PONG
如果此时服务器返回的内容为”PONG”,就表示连接成功
- Jedis数据操作
Jedis如果要进行数据操作实际上与Redis使用的命令是相同的,也就是说整体的Jedis处理的时候所使用的方法名称就是命令名称
1.设置字符串数据
2.设置有效时间的数据
3.操作Hash数据 hset、hget
4.操作List数据 lpush
5.操作set数据 sadd
6.操作SortedSet集合 zadd
7.取得对应的成绩数据:
返回Tuple,进行迭代遍历:
8.keys处理操作,使用keys可以获得全部的key的信息
取得user-*的key值
从Jedis整体的设计风格来看,不会让使用者觉得其特别复杂,相反可以会觉得容易轻松上手
- Jedis连接池
如果直接使用Jedis可以直接进行数据库的操作,但是每一次的打开和关闭实在太浪费性能了,所以为了提升操作性能,一定要使用数据库连接池的模式来进行处理,幸运的是Jedis开发包直接提供了数据库连接池的操作支持。
范例:实现数据库连接池
首先,如果想要使用Jedis连接池,则必须有一个类可以保存所有连接池相关属性的配置项,
JedisPoolConfig poolconfig = new JedisPoolConfig();
poolconfig.setMaxTotal(MAX_TOTAL);//设置最大连接数
poolconfig.setMaxIdle(MAX_IDLE);//设置空闲的连接数
poolconfig.setMaxWaitMillis(MAX_WAIT_MILLIS);//设置最大等待时间
poolconfig.setTestOnBorrow(TEST_ON_BORROW );//是否要进行连接测试,以保证返回的连接为可用连接
设置常量
public static final int MAX_TOTAL = 1000;//最大连接数
public static final int MAX_IDLE = 200;//设置最大等待时间
public static final int MAX_WAIT_MILLIS = 1000;//设置最大等待时间
public static final boolean TEST_ON_BORROW =true;//是否进行可用测试
public static final int TIMEOUT = 2000;//连接超时时间
JedisPool pool = new JedisPool(poolconfig ,reids_Host ,redis_Port,TIMEOUT,redis_Auth);
//现在所有连接被pool所管理
Jedis jedis = pool.getResource();//通过连接池获取连接对象
jedis.set("mldn","www.mldn.cn")
jedis.close();
pool.close();//关闭连接池
项目执行结束才关闭连接池(容器关闭)
以后的所有数据库操作都必须使用连接池技术完成