Springboot考勤系统

我们可以做的更好2

2018-08-12  本文已影响1人  shenyoujian

加入缓存技术,使用Redis数据库

1、首先在pom.xml中加入,jedis是java对redis操作的jar包

<!-- redis -->
        <dependency>
            <groupId>redis.clients</groupId>
            <artifactId>jedis</artifactId>
            <version>2.9.0</version>
        </dependency>

2、创建spring-redis.xml配置文件
2.1、连接池配置,配置jar包中的类,jedisPoolConfig

<!-- Redis连接池的配置 -->
    <bean id="jedisPoolConfig" class="redis.clients.jedis.JedisPoolConfig">
        <!-- 控制一个pool可分配多少个jedis实例 -->
        <property name="maxTotal" value="${redis.pool.maxActive}" />
        <!-- 连接池中最多可空闲maxIdle个连接 -->
        <property name="maxIdle" value="${redis.pool.maxIdle}" />
        <!-- 最大等待时间:当连接池中没有可用连接时,连接池等待连接被归还的最大时间,超过时间则抛出异常 -->
        <property name="maxWaitMillis" value="${redis.pool.maxWait}" />
        <!-- 在获取连接的时候检查有效性 -->
        <property name="testOnBorrow" value="${redis.pool.testOnBorrow}" />
    </bean>

2.2、创建redis.properties


image.png

因为我们在web.xml里把所有的spring文件下的spring打头的所有xml文件都统一的load进来了,加到相应的spring的配置当中。因此这些xml文件中配置是共享的。我们在spring-dao里做的配置同样spring-redis里也能共享。所以为了spring-redis.xml能读取得到redis.properties里的信息,我们不需要再spring-redis.xml里配置EncryptPropetryPlaceholderConfigurer的bean。直接在spring-dao的配置加上redis.properties就行了。
web.xml


image.png
spring-dao.xml,这两个配置就会加载进来供我们四个xml使用
image.png

3、创建jedisWritePool
这里redis包冲突了,把maven下的redis删除项目重新update就行了。不然找不到JedisPool

public class JedisPoolWriper {
    //redis连接池对象
    private JedisPool jedisPool;
    
    /**
     * 构造器
     * @param poolConfig    连接池配置相关信息
     * @param host          redis数据库位于哪个主机ip
     * @param port          访问redis数据库的端口
     */
    public JedisPoolWriper(final JedisPoolConfig poolConfig, final String host, final int port) {
        try {
            jedisPool = new JedisPool(poolConfig, host, port);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    /**
     * 获取Redis连接池对象
     * @return
     */
    public JedisPool getJedisPool() {
        return jedisPool;
    }

    /**
     * 注入Redis连接池对象
     * @param jedisPool
     */
    public void setJedisPool(JedisPool jedisPool) {
        this.jedisPool = jedisPool;
    }

}

bean配置

<!-- 创建Redis连接池,并做相关的配置 -->
    <!-- 这里可能会觉得奇怪,没有引入数据库的Properties文件,
    却可以直接获取到redis.hostname,redis.port等属性,
    原因在于web.xml中对contextconfiguration配置时引入了全部的spring-*.xml文件,
    所以这个spring-redis.xml可以共享spring-dao.xml中的配置 -->
    <bean id="jedisWritePool" class="com.imooc.o2o.cache.JedisPoolWriper"
        depends-on="jedisPoolConfig">
        <constructor-arg index="0" ref="jedisPoolConfig" />
        <constructor-arg index="1" value="${redis.hostname}" />
        <constructor-arg index="2" value="${redis.port}" type="int" />
    </bean>

4、将连接池运用到工具类里
这个工具类就是从连接池中获取jedis对象,然后进行一系列key操作,strings操作,set操作,list操作,sortset操作。。。。是我写过最长的一个java类。。。自己看文件。。。还有spring-redis文件里的bean。

5、保存不常更新的数据
有三种不常更新的数据,分别是区域信息,头条信息,店铺类别信息。
需要在service层的getAreaList方法里修改
1、流程是让这些数据先去redis里获取,
2、如果获取不到就去后台里获取
3、再把相关数据更新到redis里。
1、先注入jedis工具操作类和一个被所有成员变量共享的键变量

    @Autowired
    private JedisUtil.Keys jedisKeys;
    @Autowired
    private JedisUtil.Strings jedisStrings;

    private static String AREALISTKEY = "arealist";
@Override
    @Transactional
    public List<Area> getAreaList() {
        String key = AREALISTKEY; // 要查找jedis数据的键
        List<Area> areaList = null; // 要返回的前台的数据
        // 因为我们是用jedis的Strings类型存储的,所以值及
        // list集合需要转换为String类型然后才能存,这里就是要
        // ObjectMapper来将对象转换为json字符串
        ObjectMapper mapper = new ObjectMapper();
        // 如果redis数据库中没有存储区域信息,则先从持久化数据库中获取的区域信息
        // 然后进行类型转换,最后添加到redis数据库中
        // 然后才从redis中获取数据转换再返回前台
        if (!jedisKeys.exists(key)) {
            // 从持久化数据库中获取区域信息
            areaList = areaDao.queryArea();
            try {
                // 类型转换,将list转换为String(也就是json)
                String jsonString = mapper.writeValueAsString(areaList);
                // 将转换结果存储到redis数据对应的key中作缓存使用
                jedisStrings.set(key, jsonString);
            } catch (JsonProcessingException e) {
                e.printStackTrace();
            }

        } else {    //如果redis数据库中已经缓存了相关信息,则直接获取,然后进行转换
            String jsonString = jedisStrings.get(key);
            JavaType javaType = mapper.getTypeFactory()
                    .constructParametricType(ArrayList.class, Area.class);
            try {
                areaList = mapper.readValue(jsonString, javaType);
            } catch (IOException e) {
                e.printStackTrace();
            }   
        }
        return areaList;
    }

junit测试
首先需要让baseTest中加入扫描spring-redis.xml的配置

@ContextConfiguration({"classpath:spring/spring-dao.xml","classpath:spring/spring-service.xml","classpath:spring/spring-redis.xml"})

之前的测试,我们并不能测出是否使用了redis数据库,我们需要以debug的模式来调试,就是debug两次,先在getAreaList方法中设置断点,按f8直接跳到方法里,然后查看。

上一篇 下一篇

猜你喜欢

热点阅读