本文主要讲解的是本人代码设计的演变过程,以及使用工厂设计模式解决了什么问题
首先,我先介绍一下我将其设计为工厂设计模式的背景
我司的项目一直以来RedisTemplate来操作redis,以前一直都是在一个redis的库中所以没有什么影响,但是今天需要随时切换redis的DB,我上网查阅了一些资料,没有找到关于RedisTemplate切换DB的方式,所以我就重新封装了一下Jedis
其中有一个Jedis的连接池,我看一下源码,里面几乎全部都是构造函数
这个连接池需要自己创建,这个让我有些头疼
这个是初期的代码,使用的静态代码块初始化数据,虽然数据只初始化了一次,但是只要调用updateRedisDB()方法就会创建一个JedisPool,但是我又不能把它放到代码块中,因为这样我就无法灵活的选择JedisPool的构造函数了,所以单例就也被我淘汰了(ps:因为上面截图部分为比较low的代码,所以我没有贴出来,只是截图.....)
最后我决定使用工厂模式来解决这个问题,话不多说,上代码
import com.shengya.service.utils.PropertiesUtils; import org.apache.commons.lang3.StringUtils; import redis.clients.jedis.JedisPool; import redis.clients.jedis.JedisPoolConfig; import java.util.Map; import java.util.Properties; import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.locks.Condition; import java.util.concurrent.locks.ReentrantLock; /** * 创建JedisPool的工厂 * * @author wise * @since CreateDate 2018-05-11 16:11:30 */ public class JedisPoolFactory { private static Integer PORT; private static String HOST; private static Integer TIMEOUT = 10000; private static String PASSWORD; //缓存容器 private static Map<String, Object> cacheMap = new ConcurrentHashMap<String, Object>(); /** 静态代码块初始化参数 * @author wise * @date 2018/5/11 0011 16:30 * @param null * @return */ static { Properties p = PropertiesUtils.getProperties(); try { HOST = p.getProperty("redisHost"); String redisPort = p.getProperty("redisPort"); if (!StringUtils.isEmpty(redisPort)) { PORT = Integer.parseInt(redisPort); } PASSWORD = p.getProperty("redisPass"); } catch (Exception e1) { e1.printStackTrace(); } } /** * 获取JedisPool对象 * * @param name * @param arms * @return redis.clients.jedis * @author wise * @date 2018/5/11 0011 15:32 */ public JedisPool getJedis(String name, Object... arms) { JedisPoolConfig config = null; JedisPool jedisPool = null; if ("dataBase".equals(name)) { ReentrantLock lock = new ReentrantLock(); Condition condition = lock.newCondition(); Integer dataBase = 0; if (arms != null && arms.length > 0) { Object index = arms[0]; //判断当前参数是否是Integer类型 if (index instanceof Integer) { dataBase = (int) index; } } //查询缓存中是否存在该DB的连接池 if (cacheMap.get(name + dataBase) != null) { Object obj = cacheMap.get(name); if (obj instanceof JedisPool) { jedisPool = (JedisPool)obj; } } //缓存中不存在该DB的连接池 if (jedisPool == null) { config = new JedisPoolConfig(); config.setMaxIdle(5); config.setTestOnBorrow(false); jedisPool = new JedisPool(config, HOST, PORT, TIMEOUT, PASSWORD, dataBase); cacheMap.put(name, jedisPool); cacheMap.put(name + dataBase, dataBase); } } //如果拓展jedisPool,请在后面添加 return jedisPool; } }
我还是选择先用静态代码块来初始化参数,getJedis()方法我使用一个name参数来判断当前要创建的JedisPool,使用可变参数来传递数据,为避免同样的redis库重复创建jedisPool,我使用了ConcurrentHashMap做缓存,每次在创建一次先进行一次判断,以后如果需要再创建其它的JedisPool的话直接在后面加上else if即可,拓展起来非常方便
如果您对我的看法有更好的意见或建议,请随时私信我或者在评论区留言,不吝赐教
版权声明:本文为博主原创文章,转载请注明出处(https://blog.csdn.net/F1004145107/article/details/80281722)