CAS4.0分布式部署以及使用Redis缓存共享ticket

CAS4.0分布式部署以及使用Redis缓存共享ticket

         当业务不断拓展,系统用户在不断增加时,我们的平台统一登录认证服务无法承受当前压力。此时,我们需要分布式部署我们的统一登录认证服务。

         CAS的分布式部署,除了注意session共享,通过nginx或者apache反向代理外,还需要注意票据ticket的存储共享。

         ticketRegistry.xml文件中,配置ticket相关的信息。主要配置:1.注册ticket存储,2.定时清除过期ticket

         由于我们使用的Redis缓存Key设置了过期时间,因此可以注释掉清除过期ticket的定时器及相关类。

         编写新的ticket存储类需要继承类AbstractDistributedTicketRegistry。代码如下:

    

package cas.ticket;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.util.Collection;

import org.jasig.cas.ticket.Ticket;
import org.jasig.cas.ticket.TicketGrantingTicket;
import org.jasig.cas.ticket.registry.AbstractDistributedTicketRegistry;

import cn.net.xinyi.util.SysPropertiesUtil;
import redis.clients.jedis.Jedis;
import redis.clients.jedis.JedisPool;
import redis.clients.jedis.JedisPoolConfig;

/**
 * 使用Redis存储Ticket
 * @author XIVA
 */
public class RedisTicketRegistry extends AbstractDistributedTicketRegistry
{

    private static int redisDatabaseNum;

    private static String hosts;
    
    private static int port;
    
    private static int connTimeout;
    
    private static String redisPassword;

    /**
     * ST最大空闲时间
     */
    private static int st_time;

    /**
     * TGT最大空闲时间
     */
    private static int tgt_time;

    private static JedisPool cachePool;

    static
    {
        redisDatabaseNum = SysPropertiesUtil.getPropertyInt("redis_database_num");

        hosts = SysPropertiesUtil.getProperty("redis_hosts");
        
        port = SysPropertiesUtil.getPropertyInt("redis_port");

        connTimeout = SysPropertiesUtil.getPropertyInt("redis_conn_timeout");
        
        redisPassword = SysPropertiesUtil.getProperty("redis_password");

        st_time = SysPropertiesUtil.getPropertyInt("st_time");

        tgt_time = SysPropertiesUtil.getPropertyInt("tgt_time");

        cachePool = new JedisPool(new JedisPoolConfig(), hosts, port, connTimeout, redisPassword);
    }

    @Override
    public void addTicket(Ticket ticket)
    {
        Jedis jedis = cachePool.getResource();

        jedis.select(redisDatabaseNum);

        int seconds = 0;

        String key = ticket.getId();

        if (ticket instanceof TicketGrantingTicket)
        {
            seconds = tgt_time / 1000;
        }
        else
        {
            seconds = st_time / 1000;
        }

        ByteArrayOutputStream bos = new ByteArrayOutputStream();
        ObjectOutputStream oos = null;

        try
        {

            oos = new ObjectOutputStream(bos);

            oos.writeObject(ticket);

        }
        catch (Exception e)
        {
            logger.error("adding ticket to redis error.");
        }
        finally
        {
            try
            {
                if (null != oos)
                    oos.close();

            }
            catch (Exception e)
            {
                logger.error("oos closing error when adding ticket to redis.");
            }
        }

        jedis.set(key.getBytes(), bos.toByteArray());
        jedis.expire(key.getBytes(), seconds);
        jedis.close();

    }

    @Override
    public boolean deleteTicket(String ticketId)
    {
        if (ticketId == null)
        {
            return false;
        }

        Jedis jedis = cachePool.getResource();
        jedis.select(redisDatabaseNum);
        
        jedis.del(ticketId.getBytes());
        jedis.close();
        return true;
    }

    @Override
    public Ticket getTicket(String ticketId)
    {
        return getProxiedTicketInstance(getRawTicket(ticketId));
    }

    private Ticket getRawTicket(final String ticketId)
    {
        if (null == ticketId)
        {
            return null;
        }

        Jedis jedis = cachePool.getResource();
        jedis.select(redisDatabaseNum);
        Ticket ticket = null;
        byte[] bytes = jedis.get(ticketId.getBytes());
        if (bytes == null || bytes.length < 1)
        {
            return null;
        }
        ByteArrayInputStream bais = new ByteArrayInputStream(bytes);
        ObjectInputStream ois = null;

        try
        {
            ois = new ObjectInputStream(bais);
            ticket = (Ticket) ois.readObject();
        }
        catch (Exception e)
        {
            e.printStackTrace();
            logger.error("getting ticket to redis error.");
        }
        finally
        {
            try
            {
                if (null != ois)
                {
                    ois.close();
                }
            }
            catch (Exception e)
            {
                e.printStackTrace();
                logger.error("ois closing error when getting ticket to redis.");
            }
        }

        jedis.close();
        return ticket;
    }

    @Override
    public Collection<Ticket> getTickets()
    {
        throw new UnsupportedOperationException("GetTickets not supported.");  
    }

    @Override
    protected boolean needsCallback()
    {
        return false;
    }

    @Override
    protected void updateTicket(Ticket ticket)
    {
        this.addTicket(ticket);  
    }

}

 

    变更后的ticketRegistry.xml代码如下:

     

<?xml version="1.0" encoding="UTF-8"?>
<!--

    Licensed to Jasig under one or more contributor license
    agreements. See the NOTICE file distributed with this work
    for additional information regarding copyright ownership.
    Jasig licenses this file to you under the Apache License,
    Version 2.0 (the "License"); you may not use this file
    except in compliance with the License.  You may obtain a
    copy of the License at the following location:

      http://www.apache.org/licenses/LICENSE-2.0

    Unless required by applicable law or agreed to in writing,
    software distributed under the License is distributed on an
    "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
    KIND, either express or implied.  See the License for the
    specific language governing permissions and limitations
    under the License.

-->
<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"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
    <description>
    	Configuration for the default TicketRegistry which stores the tickets in-memory and cleans them out as specified intervals.
    </description>
       
  <!-- Ticket Registry 
  <bean id="ticketRegistry" class="org.jasig.cas.ticket.registry.DefaultTicketRegistry" />
  -->
  
  <!-- ticket store on redis db	-->
  <bean id="ticketRegistry" class="cas.ticket.RedisTicketRegistry" />
  
	<!--Quartz -->
	<!-- TICKET REGISTRY CLEANER 
	<bean id="ticketRegistryCleaner" class="org.jasig.cas.ticket.registry.support.DefaultTicketRegistryCleaner"
		p:ticketRegistry-ref="ticketRegistry"
		p:logoutManager-ref="logoutManager" />
	
	<bean id="jobDetailTicketRegistryCleaner" class="org.springframework.scheduling.quartz.MethodInvokingJobDetailFactoryBean"
		p:targetObject-ref="ticketRegistryCleaner"
		p:targetMethod="clean" />
	
	<bean id="triggerJobDetailTicketRegistryCleaner" class="org.springframework.scheduling.quartz.SimpleTriggerBean"
		p:jobDetail-ref="jobDetailTicketRegistryCleaner"
		p:startDelay="20000"
		p:repeatInterval="5000000" /> -->
</beans>

 

    

    

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值