Spring之redisyi一主一从复制(非哨兵模式)
看了好几天redis了,公司从刚开始的redisluster变成了redis主从,原因是rediscluster不可控,其实是我水平没到,万一出点啥事,我这个负责人都解决不了,那就完了!大数据平台下,如果缓存崩了,所有操作提前全都干到数据库,很能造成数据库的崩溃,所以改用简单的主从复制模式,这样即可控,又直观,下面我将自己这几天整理的代码整理如下:
如果配置一主一从的redis服务:在使用pool的时候要注意,jedis提供两个pool:JedisPool和ShardedJedisPool ,本文使用JedisPool。
数据量较大时需要shard(多机环境),这个时候要用ShardedJedisPool。ShardedJedis是基于一致性哈希算法实现的分布式Redis集群客户端
注意:使用该代码前提是:成功安装redis并已经启动redis主从服务,否则拒绝连接,那是很。。。的
工程目录:

本人习惯:按目录顺序一次往下帖代码
1、创建加载连接池工具
package com.test.connection;
import redis.clients.jedis.Jedis;
import redis.clients.jedis.JedisPool;
public class ClientConnect {
//主库
private JedisPool masterJedisPool;
//从库
private JedisPool slaveJedisPool;
//设置主库
public void setMasterJedisPool(JedisPool masterJedisPool) {
this.masterJedisPool = masterJedisPool;
}
//设置从库
public void setSlaveJedisPool(JedisPool slaveJedisPool) {
this.slaveJedisPool = slaveJedisPool;
}
//获取主库
public Jedis getMasterJedisPool() {
Jedis jedis=null;
try{
jedis=masterJedisPool.getResource();
}catch(Exception e){
e.printStackTrace();
masterJedisPool.returnBrokenResource(jedis);
}
return jedis;
}
//获取从库
public Jedis getSlaveJedisPool() {
Jedis jedis=null;
try{
jedis=slaveJedisPool.getResource();
}catch(Exception e){
e.printStackTrace();
slaveJedisPool.returnBrokenResource(jedis);
}
return jedis;
}
/**
* 关闭池
* @param Jedis
* @param flag flag=1为从库,flag=0为主库
*/
@SuppressWarnings("deprecation")
public void closeJedisPool(Jedis jedis,int flag) {
if(flag==0){
masterJedisPool.close();
System.out.println("开始返回主Pool资源。。。");
if(masterJedisPool.isClosed()){
try{
masterJedisPool.returnResource(jedis);
System.out.println("返回主Pool资源成功");
}catch(Exception e){
e.printStackTrace();
}
}
}
if(flag==1){
slaveJedisPool.close();
System.out.println("开始返回从Pool资源。。。");
if(slaveJedisPool.isClosed()){
try{
slaveJedisPool.returnResource(jedis);
System.out.println("返回从Pool资源成功");
}catch(Exception e){
e.printStackTrace();
}
}
}
}
}
2、为了好看和隐私性强,创建加载路径
package com.test.constant;
public class SysConstants {
public static final String PATH = "classpath:/context/applicationContext.xml";
public static final String BEAN="clientConnect";
}
3、创建实体类
package com.test.entities;
public class User {
protected String companyId;
public String getCompanyId() {
return companyId;
}
public void setCompanyId(String companyId) {
this.companyId = companyId;
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getAge() {
return age;
}
public void setAge(String age) {
this.age = age;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
public String getTell() {
return tell;
}
public void setTell(String tell) {
this.tell = tell;
}
protected String id;
protected String name;
protected String age;
protected String address;
protected String tell;
}
4、创建操作主数据库的工具方法:
package com.test.Impl;
import java.util.List;
import com.test.entities.User;
import redis.clients.jedis.Jedis;
/**
*
* @author root
*操作主库,实现增、删、改功能
*/
public class MasterRedisImpl {
Jedis jedis;
public MasterRedisImpl(Jedis jedis){
this.jedis=jedis;
}
/**
* 添加
* @param list
*/
public void INSERT(List<User> list) {
for(int i=0;i<list.size();i++){
User user=list.get(i);
//主键
String key = "user:userId:"+user.getId();
//值1
String field1 = "name:";
String value1 = user.getName();
jedis.hset(key, field1, value1);
//值2
String field2 = "age:";
String value2 = user.getAge();
jedis.hset(key, field2, value2);
//值3
String field3 = "address:";
String value3 = user.getAddress();
jedis.hset(key, field3, value3);
//值4
String field4 = "tell:";
String value4 = user.getTell();
jedis.hset(key, field4, value4);
/**
* 添加键值list
* key1=user:userId:
* value1=1,2,3,4,5,6
*
* key2=user:name:
* value2=zhao,hai,dong
*
* key3=user:age
* value3=11,12 ,12,13
*/
//id->list
String listKey="user:userId:";
String listValue="user:userId:"+user.getId();
jedis.lpush(listKey, listValue);
//name->list
String listKey1="user:name:";
String listValue1="user:name:"+user.getName()+":"+user.getId();
jedis.rpush(listKey1, listValue1);
// 添加外键
jedis.sadd("user:userId:"+user.getId()+":companyId:", user.getCompanyId());
}
}
/**
* 删除hash表中指定key的n个指定字段
*
* @param key
* @param fields
*/
public void DELETE(String key,String []fields){
String field=null;
for(int i=0;i<fields.length;i++){
field=fields[i];
jedis.hdel(key, field); //删除xjj.h1中的f1和f2
}
}
/**
* 删除hash表中指定key的所有字段
*/
public void DELETEVALUE(String key){
jedis.del(key);
}
/**
* 移除集合中一个或多个成员
*/
public void DELETESET(String key,String []fields){
String field=null;
for(int i=0;i<fields.length;i++){
field=fields[i];
jedis.srem(key, field);
}
}
/**
* LPOP key:移出并获取列表的第一个元素
* @param key
*/
public String DELETELIST(String key){
return jedis.lpop(key);
}
}
5、创建操作从数据库的工具方法:
package com.test.Impl;
import java.util.List;
import java.util.Set;
import redis.clients.jedis.Jedis;
/**
*
* @author root
*读取从库读数据
*/
public class SlaveRedisImpl {
Jedis jedis;
public SlaveRedisImpl(Jedis slaveJedis) {
this.jedis=slaveJedis;
}
/**
* 查询
* 返回哈希表 key中给定域 field的值
*/
public String SELECT(String key,String field){
return jedis.hget(key, field);
}
public String SELECT(String key){
return jedis.get(key);
}
/**
* 查询list,获取指定位置的元素
* @param key
* @return
*/
public List<String> SELECTLIST(String key,int start,int end){
return jedis.lrange(key, start, end);
}
/**
* 在set中获取key对应所有的vlaue
* @param key
* @return
*/
public Set<String> SELECTSET(String key){
return jedis.smembers(key);
}
}
6、创建applicationContext.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:p="http://www.springframework.org/schema/p"
xmlns:mvc="http://www.springframework.org/schema/mvc" xmlns:context="http://www.springframework.org/schema/context"
xmlns:util="http://www.springframework.org/schema/util"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd
http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd
http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util-3.0.xsd">
<context:property-placeholder location="classpath:/property/redis.properties" />
<!-- 连接池配置 -->
<bean id="poolConfig" class="redis.clients.jedis.JedisPoolConfig">
<property name="maxIdle" value="${redis.maxIdle}" />
<property name="maxTotal" value="${redis.maxTotal}" />
<property name="maxWaitMillis" value="${redis.maxWaitMillis}" />
<property name="testOnBorrow" value="${redis.testOnBorrow}" />
</bean>
<!-- 连接池 -->
<bean id="masterJedisPool" class="redis.clients.jedis.JedisPool">
<constructor-arg index="0" ref="poolConfig"/>
<constructor-arg index="1" value="127.0.0.1" type="java.lang.String"/>
<constructor-arg index="2" value="6379" type="int"/>
</bean>
<bean id="slaveJedisPool" class="redis.clients.jedis.JedisPool">
<constructor-arg index="0" ref="poolConfig"/>
<constructor-arg index="1" value="127.0.0.1" type="java.lang.String"/>
<constructor-arg index="2" value="6380" type="int"/>
</bean>
<bean id="clientConnect" class="com.test.connection.ClientConnect">
<property name="masterJedisPool" ref="masterJedisPool"/>
<property name="slaveJedisPool" ref="slaveJedisPool"/>
</bean>
</beans>
连接池配置文件redis.properties:
redis.maxIdle=300
redis.maxTotal=600
redis.maxWaitMillis=1000
redis.testOnBorrow=true
下来当然是测试了:
package com.test.main;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.Set;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import com.test.Impl.MasterRedisImpl;
import com.test.Impl.SlaveRedisImpl;
import com.test.connection.ClientConnect;
import com.test.constant.SysConstants;
import com.test.entities.User;
import redis.clients.jedis.Jedis;
public class Test {
/**
* 节点信息
* redis.clients.jedis.Jedis@6ceadf59
* redis.clients.jedis.Jedis@e3b7c27
* @param args
*/
public static void main(String[] args) {
@SuppressWarnings("resource")
ApplicationContext ctx = new ClassPathXmlApplicationContext(SysConstants.PATH);
ClientConnect redisUtils = (ClientConnect) ctx.getBean(SysConstants.BEAN);
List<User>list=new ArrayList<>();
for(int i=0;i<10;i++){
User user=new User();
user.setId(i+"");
user.setAddress("gansu"+i);
user.setAge(i+"");
user.setName("zhd"+i);
user.setCompanyId("1010111"+i);
user.setTell("15309853180");
list.add(user);
}
//获取主redis库
Jedis mastrJedis=redisUtils.getMasterJedisPool();
//操作主redis库
MasterRedisImpl mastedao=new MasterRedisImpl(mastrJedis);
//添加数据
mastedao.INSERT(list);
//获取从redis库
Jedis slaveJedis=redisUtils.getSlaveJedisPool();
//操作从redis库
SlaveRedisImpl slavedao=new SlaveRedisImpl(slaveJedis);
//查询
String keyHash="user:userId:5";
String filed="name:";
String keyList="user:name:";
int start=0;
int end=2;
String keySet="user:userId:4:companyId:";
String hashValue=slavedao.SELECT(keyHash,filed);
System.out.println("hashValue:"+hashValue);
List<String> listValue=slavedao.SELECTLIST(keyList, start,end);
System.out.println("listValue:"+listValue.toString());
Set<String> valueSet=slavedao.SELECTSET(keySet);
Iterator<String> it = valueSet.iterator();
while (it.hasNext()) {
String str = it.next();
System.out.println("valueSet:"+str);
}
}
}
以上代码,是我自己整理的,并且完全可以使用的代码,小菜鸟门完全可以复制粘帖;
Spring之redisyi一主一从复制(非哨兵模式)的更多相关文章
- Redis-02-主从复制和哨兵模式
安全认证 开启认证 redis默认开启了保护模式,只允许本地回环地址登录并访问数据库 修改redis的配置文件,并重启redis的服务 vim /opt/redis_cluster/redis_637 ...
- MySQL 5.7--多源复制(非GTID模式)
==================================================== 在MYSQL5.7版本中引入多源复制,一个从库允许复制多个主库的数据,每个主库被配置为一个单独 ...
- Spring WebFlux, 它是一种异步的, 非阻塞的, 支持背压(Back pressure)机制的Web 开发WebFlux 支持两种编程风(姿)格(势) 使用@Controller这种基于注解
概述 什么是 Spring WebFlux, 它是一种异步的, 非阻塞的, 支持背压(Back pressure)机制的Web 开发框架. 要深入了解 Spring WebFlux, 首先要了知道 R ...
- Socket 阻塞模式和非阻塞模式
阻塞I/O模型: 简介:进程会一直阻塞,直到数据拷贝 完成 应用程序调用一个IO函数,导致应用程序阻塞,等待数据准备好. 如果数据没有准备好,一直等待….数据准备好了,从内核拷贝到用户空间,IO函数返 ...
- ORACLE归档模式和非归档模式的利与弊
转: 在Oracle数据库中,主要有两种日志操作模式,分别为非归档模式与归档模式.默认情况下,数据库采用的是非归档模式.作为一个合格的数据库管理员,应当深入了解这两种日志操作模式的特点,并且在数据库建 ...
- spring整合redis(哨兵模式)
首先服务器搭建哨兵模式(我这里使用的是Windows8系统),感谢两位博主,少走不少弯路,在此给出链接:服务器哨兵模式搭建和整合哨兵模式 什么一些介绍就不介绍了,可以看一下连接,比较详细,初次接触,当 ...
- Oracle之归档模式与非归档模式
归档模式和非归档模式 在DBA部署数据库之初,必须要做出的最重要决定之一就是选择归档模式(ARCHIVELOG)或者非 归档模式(NOARCHIVELOG )下运行数据库.我们知道,Oracle 数据 ...
- Oracle之rman数据库在非归档模式下的备份和恢复
1.数据库在非归档模式下的备份 SQL> archive log list;数据库日志模式 非存档模式自动存档 禁用存档终点 USE_DB_RECOVERY_FILE_DEST最早的联机日志序列 ...
- MySQL MHA--故障切换模式(GTID模式和非GTID模式)
GTID和非GTID故障切换模式选择 MySQL 5.6版本引入GTID来解决主从切换时BINLOG位置点难定位的问题,MHA从0.56版本开始支持基于GTID的复制,在切换时可以采用GTID模式和非 ...
随机推荐
- Rx编程的第一步是将native对象转换为monad对象
Rx编程的第一步是将native对象转换为monad对象 将基础类型转换为高阶类型,以便使用函数式编程的特性.
- lua-resty-gearman模块
粘贴一段百度对gearman的解释: Gearman是一个用来把工作委派给其他机器.分布式的调用更适合做某项工作的机器.并发的做某项工作在多个调用间做负载均衡.或用来在调用其它语言的函数的系统. lu ...
- WorldWind源码剖析系列:大气层散射球类AtmosphericScatteringSphere
大气层散射球类AtmosphericScatteringSphere代表地球外面的大气层散射球模型,可以控制开启/关闭渲染该对象.该类的类图如下. 该类所包含的主要字段.属性和方法如下: public ...
- js倒计时,页面刷新时,不会从头计时
最近不忙,瞎鼓捣...哈哈 这里利用了H5的本地存储 localStorage,取秒数直接用了php的time()方法,就懒得用js取了. 把第一次访问页面时的时间存在客户端,然后再刷新的时候,比较用 ...
- strstr(),strchr()
strstr($a, $b)和strchr()一样,起的别名,表示查找$a中第一次出现$b,并返回字符串的剩余部分: .strrchr()从后往前查第一个出现的 直接写两行代码: <?php $ ...
- 降阶法计算行列式方法有个地方有Bug(原文也已更正,此为更正后部分)
今天用此函数做方程求解时发现有误,特此更正: /// <summary> /// 降阶法计算行列式 /// </summary> /// <param name=&quo ...
- 微服务RPC框架选美
原文:http://p.primeton.com/articles/59030eeda6f2a40690f03629 1.RPC 框架谁最美? Hello,everybody!说到RPC框架,可能大家 ...
- 20155238 《JAVA程序设计》实验二(Java面向对象程序设计)实验报告
实验内容 初步掌握单元测试和TDD 理解并掌握面向对象三要素:封装.继承.多态 初步掌握UML建模 熟悉S.O.L.I.D原则 了解设计模式 实验要求 1.没有Linux基础的同学建议先学习<L ...
- 在java代码中执行js脚本,实现计算出字符串“(1+2)*(1+3)”的结果
今天在公司项目中,发现一个计算运费的妙招.由于运费规则各种各样,因此写一个公式存到数据库.下次需要计算运费时,直接取出这个公式,把公式的未知变量给替换掉,然后计算出结果就是ok了. 一 ...
- Spring集成Swagger,Java自动生成Api文档
博主很懒... Swagger官网:http://swagger.io GitHub地址:https://github.com/swagger-api 官方注解文档:http://docs.swagg ...