最新历史版本 :配置 FineBI 作为 CAS 客户端 返回文档
编辑时间: 内容长度:图片数:目录数: 修改原因:

目录:

1. 概述编辑

本文介绍如何配置 FineBI 作为 CAS 客户端。

1.1 环境检查

在配置 FineBI 之前,需要按如下步骤配置好环境:

1)CAS 服务器搭建,若用户已有 CAS 环境,可忽略该操作。

2)配置 SSL 证书实现 HTTPS 访问

3)实现基于数据库的身份验证 ,若用户无需使用数据库中的信息进行登录验证,可忽略该操作。

1.2 操作原理

CAS 单点登录 过程中,根据客户端承担的主要功能,对 FineBI 进行相应配置。

1)用户访问 FineBI 系统时,将请求重定向到 CAS 服务器。

2)向 CAS 服务器验证 ticket 的真实性,是否过期等信息。

3)获取 CAS 认证返回的用户名,并且和 FineBI 中的用户进行对比,对比一致,且用户可用,则单点登录成功。

登录认证流程如下图所示:

2. 操作步骤编辑

2.1 拷贝 BI 工程

%FineBI%/webapps下的 webroot 文件拷贝到%Tomcat_HOME%/webapps下。

注:BI 工程名 webroot 可以自定义修改,但是需要注意的是后面访问 BI 工程时地址http://ip:端口/工程名/decision中的工程名也要随之更改。

1576487101509101.png

2.2 拷贝 JAR 包

将 CAS 的casclient.jar 和cas-client-core-3.2.1.jar JAR 包和%Java_HOME%/jdk/lib/tools.jar都拷贝到%TOMCAT_HOME%/webapps/webroot/WEB-INF/lib下,如下图所示:

3.png

2.3 添加 web.xml

web.xml 文件用来实现以下功能:

  • 用户访问 FineBI 系统时,将请求重定向到 CAS 服务器。

  • 向 CAS 服务器验证 ticket 的真实性,是否过期等信息。

%TOMCAT_HOME%webapps/webroot/WEB-INF目录下新建web.xml 文件,插入代码如下所示:

<?xml version="1.0" encoding="UTF-8"?>
<web-app 
   xmlns="http://java.sun.com/xml/ns/j2ee" 
   xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
   xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd" 
   version="2.4"> 
  <display-name>Template WebApp</display-name>
    <mime-mapping>
  <extension>msi</extension>
  <mime-type>application/x-msi</mime-type>
  </mime-mapping>     
  <filter>  
        <filter-name>CASFilter</filter-name>  
        <filter-class>edu.yale.its.tp.cas.client.filter.CASFilter</filter-class>  
        <init-param>  
            <param-name>edu.yale.its.tp.cas.client.filter.loginUrl</param-name>  
            <param-value>https://roxy:8443/cas/login</param-value>  
            <!--cas提供登录页面的url-->  
        </init-param>  
        <init-param>  
            <param-name>edu.yale.its.tp.cas.client.filter.validateUrl</param-name>  
            <param-value>https://roxy:8443/cas/proxyValidate</param-value>  
            <!--cas提供service ticker或者proxy ticket验证服务的url-->  
        </init-param>  
        <init-param>  
            <param-name>edu.yale.its.tp.cas.client.filter.serverName</param-name>  
            <param-value>roxy:8443</param-value>  
                        <!--客户端应用的域名和端口-->  
        </init-param>  
    </filter>  
    <filter-mapping>  
        <filter-name>CASFilter</filter-name>  
        <url-pattern>/decision/*</url-pattern>  
    </filter-mapping> 
 <filter>    
    <filter-name>FrFilter</filter-name>    
    <filter-class>com.fr.FrFilter</filter-class>    
</filter>    
<filter-mapping>    
    <filter-name>FrFilter</filter-name>    
    <url-pattern>/decision/*</url-pattern>    
</filter-mapping>  
</web-app>

其中 roxy 为个人配置的域名,请按照个人设置进行修改,如下图所示:

5.png

2.4 新建 Java 文件

Fr.Filter 用来获取 CAS 认证返回的用户名,并且和 FineBI 中的用户进行对比,判断是否为 FineBI 系统的用户。

1)新建 Java 文件,命名为 FrFilter.java 。完整的 Java 代码如下所示:

Java 代码见链接:FrFilter.java

package com.fr;
import com.fr.data.NetworkHelper;
import com.fr.decision.mobile.terminal.TerminalHandler;
import com.fr.decision.webservice.utils.DecisionServiceConstants;
import com.fr.decision.webservice.v10.login.LoginService;
import com.fr.general.ComparatorUtils;
import com.fr.log.FineLoggerFactory;
import com.fr.security.JwtUtils;
import com.fr.stable.StringUtils;
import com.fr.stable.web.Device;
import org.jasig.cas.client.validation.Assertion;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.io.IOException;
/**
 * Created by Zed on 2018/9/11.
 */
public class FrFilter implements Filter {
    public FrFilter() {
    }
    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
    }
    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        FineLoggerFactory.getLogger().info("fr cas login");
        HttpServletRequest req = (HttpServletRequest) servletRequest;
        HttpServletResponse res = (HttpServletResponse) servletResponse;
        HttpSession session = req.getSession(true);
        FineLoggerFactory.getLogger().info("URL:" + req.getRequestURI());
        String username;
        //获取cas传递过来的username
        Object object = req.getSession().getAttribute("_const_cas_assertion_");
        if (object != null) {
            Assertion assertion = (Assertion) object;
            username = assertion.getPrincipal().getName();
        } else {
            username = (String) session.getAttribute("edu.yale.its.tp.cas.client.filter.user");
        }
        try {
            //用户名为空,登录请求有问题,直接报错
            if (StringUtils.isNotEmpty(username)) {
                FineLoggerFactory.getLogger().info("username:" + username);
                //获取请求携带的token
                Object oldToken = session.getAttribute(DecisionServiceConstants.FINE_AUTH_TOKEN_NAME);
                //token不存在,或者token过期了,走后台登录方法
                if (oldToken == null || !checkTokenValid(req, (String) oldToken, username)) {
                    login(req, res, session, username);
                    filterChain.doFilter(req, res);
                } else {
                    //放行
                    filterChain.doFilter(req, res);
                    FineLoggerFactory.getLogger().info("no need");
                }
            } else {
                throw new Exception("username is empty");
            }
        } catch (Exception e) {
            FineLoggerFactory.getLogger().error(e.getMessage(), e);
        }
    }
    /**
     * 后台登录方法
     */
    private void login(HttpServletRequest req, HttpServletResponse res, HttpSession session, String username) throws Exception {
        String token = LoginService.getInstance().login(req, res, username);
        req.setAttribute(DecisionServiceConstants.FINE_AUTH_TOKEN_NAME, token);
        FineLoggerFactory.getLogger().info("fr FrFilter is over with username is ###" + username);
    }
    /**
     * 校验token是否有效
     */
    private boolean checkTokenValid(HttpServletRequest req, String token, String currentUserName) {
        try {
            //当前登录用户和token对应的用户名不同,需要重新生成token
            if (!ComparatorUtils.equals(currentUserName, JwtUtils.parseJWT(token).getSubject())) {
                FineLoggerFactory.getLogger().info("username changed:" + currentUserName);
                return false;
            }
            Device device = NetworkHelper.getDevice(req);
            LoginService.getInstance().loginStatusValid(token, TerminalHandler.getTerminal(req, device));
            return true;
        } catch (Exception ignore) {
        }
        return false;
    }
    @Override
    public void destroy() {
    }
}

2)编译 FrFilter.java ,将生成的 FrFilter.class 文件放在%TOMCAT_HOME%\webroot\WEB-INF\classes\com\fr目录下,如下图所示:

点击下载并解压获得 FrFilter.class 文件:FrFilter.zip

2.png

3. 效果查看编辑

启动 Tomcat 服务器,在浏览器中输入:https://localhost:8443/webroot/decision即进入了 CAS 登录界面,输入用户名和密码即可跳转到数据决策系统对应的用户界面下,如下图: