热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

使用php处理cas认证

最近项目要嵌入到平台上做一个应用,数据对接用ms-security(见上篇博客),登录则使用cas认证,今天就把完整代码放进来,也是走了好些个弯路的。代码的主要逻辑就是,当用户访问应

最近项目要嵌入到平台上做一个应用,数据对接用ms-security(见上篇博客),登录则使用cas认证,今天就把完整代码放进来,也是走了好些个弯路的。


代码的主要逻辑就是,当用户访问应用时,应用检测是否已登录,未登录则带上本地url跳转到cas登录中心,用户输入用户名、密码后,正确的话便带上ticket跳转到一开始带上的url(通常是该应用的登录接口),检测到ticket后便使用file_get_contents方法读取cas认证的页面,之后获取到想要的用户名,使用该用户名去该应用的用户表查找记录session并登录。


// cas服务器登录地址
$loginServer = "http://cas/sso/login";

// cas服务器验证地址
$validateServer = "http://cas/sso/serviceValidate";

// cas服务器回调地址
$address = "http://app/exam/";

// 若有回调地址,便在url里追加上
if (isset($_REQUEST["redirectUrl"]) && !empty($_REQUEST["redirectUrl"])) {
    $address .= "?redirectUrl=" . $_REQUEST["redirectUrl"];
}

// 如果请求带有ticket
if (isset($_REQUEST["ticket"]) && !empty($_REQUEST["ticket"])) {
    try {

        // url里带上ticket去cas服务验证地址
        $validateurl = $validateServer . "?ticket=" . $_REQUEST["ticket"] . "&service=" . $address;
        header("Content-Type:text/html;charset=utf-8");

        // 后去验证后的内容
        $validateResult = str_replace('cas:', '', file_get_contents($validateurl));
        $validateXML = simplexml_load_string($validateResult);
        $successnode = $validateXML->authenticationSuccess[0];

        // 验证成功
        if (!empty($successnode)) {

            // 获取用户名,并在该系统内查询用户相关的信息
            $account = (string)$successnode->user;
            $auth = M('Auth')->where(array('a_account' => $account))->field('a_id, s_id, a_account')->find();

            // 保存session
            setPassportId($auth['a_id']);

            //  保存登录信息
            $info['a_id'] = $auth['a_id'];
            $info['a_last_login_time'] = time();
            $info['a_last_login_ip'] = ip2long(get_client_ip());
            $info['a_login_count'] = array('exp', 'a_login_count+1');
            M('Auth')->save($info);

            // 加入登陆统计表
            $map = array();
            $map['l_year'] = date('Y', time());
            $map['l_month'] = date('m', time());
            $map['a_id'] = $auth['a_id'];
            $map['s_id'] = $auth['s_id'];
            $l_id = M('Login')->where($map)->getField('l_id');

            if ($l_id) {
                $map['l_count'] = array('exp', 'l_count+1');
                M('Login')->where(array('l_id' => $l_id))->save($map);
            } else {
                $map['l_count'] = 1;
                M('Login')->add($map);
            }

            redirect(__APP__ . '/Index');

            // 若验证失败,如ticket过期、不合法的service,则重新认证
        } else {
            header("Location: " . $loginServer . "?service=" . $address);
            exit;
        }
    } catch (Exception $e) {
        echo "出错了";
        echo $e->getMessage();
    }

    // 否则就去cas登录地址
} else {
    header("Location: " . $loginServer . "?service=" . $address);
    exit;
}


这里遇到的一个问题是认证返回的cas相关的xml是带有命名空间的,一开始(代码中没有使用str_replace)怎么都解析不了,后来到论坛问了下,之后自己又找了下xml的相关信息,最后用str_replace去掉了命名空间(namespace)之后解析正常,于是去论坛看看有朋友解答么,打开问题后,发现两位坛主说了下看法,其中唠叨大大不愧是经验丰富的,正确给出了答案,但是最下面的那个在我机子上没有解析出来

$str = <<
    
        zhangjian
        
    

EOT;
  
  
 
$validateXML = simplexml_load_string($str, null, 0, 'cas', true);
print_r($validateXML);
 
$successnode = $validateXML->authenticationSuccess[0];
print_r($successnode);
 
// 此方法还是没有解析出来
$xml = new DOMDocument();
$xml -> loadXML($str);
print_r($xml);




推荐阅读
  • 解决Sharepoint 2013运行状况分析出现的“一个或多个服务器未响应”问题的方法
    本文介绍了解决Sharepoint 2013运行状况分析中出现的“一个或多个服务器未响应”问题的方法。对于有高要求的客户来说,系统检测问题的存在是不可接受的。文章详细描述了解决该问题的步骤,包括删除服务器、处理分布式缓存留下的记录以及使用代码等方法。同时还提供了相关关键词和错误提示信息,以帮助读者更好地理解和解决该问题。 ... [详细]
  • 本文介绍了通过ABAP开发往外网发邮件的需求,并提供了配置和代码整理的资料。其中包括了配置SAP邮件服务器的步骤和ABAP写发送邮件代码的过程。通过RZ10配置参数和icm/server_port_1的设定,可以实现向Sap User和外部邮件发送邮件的功能。希望对需要的开发人员有帮助。摘要长度:184字。 ... [详细]
  • Nginx使用(server参数配置)
    本文介绍了Nginx的使用,重点讲解了server参数配置,包括端口号、主机名、根目录等内容。同时,还介绍了Nginx的反向代理功能。 ... [详细]
  • Centos7.6安装Gitlab教程及注意事项
    本文介绍了在Centos7.6系统下安装Gitlab的详细教程,并提供了一些注意事项。教程包括查看系统版本、安装必要的软件包、配置防火墙等步骤。同时,还强调了使用阿里云服务器时的特殊配置需求,以及建议至少4GB的可用RAM来运行GitLab。 ... [详细]
  • 如何使用Java获取服务器硬件信息和磁盘负载率
    本文介绍了使用Java编程语言获取服务器硬件信息和磁盘负载率的方法。首先在远程服务器上搭建一个支持服务端语言的HTTP服务,并获取服务器的磁盘信息,并将结果输出。然后在本地使用JS编写一个AJAX脚本,远程请求服务端的程序,得到结果并展示给用户。其中还介绍了如何提取硬盘序列号的方法。 ... [详细]
  • http:my.oschina.netleejun2005blog136820刚看到群里又有同学在说HTTP协议下的Get请求参数长度是有大小限制的,最大不能超过XX ... [详细]
  • WebSocket与Socket.io的理解
    WebSocketprotocol是HTML5一种新的协议。它的最大特点就是,服务器可以主动向客户端推送信息,客户端也可以主动向服务器发送信息,是真正的双向平等对话,属于服务器推送 ... [详细]
  • 解决nginx启动报错epoll_wait() reported that client prematurely closed connection的方法
    本文介绍了解决nginx启动报错epoll_wait() reported that client prematurely closed connection的方法,包括检查location配置是否正确、pass_proxy是否需要加“/”等。同时,还介绍了修改nginx的error.log日志级别为debug,以便查看详细日志信息。 ... [详细]
  • 本文讨论了如何使用Web.Config进行自定义配置节的配置转换。作者提到,他将msbuild设置为详细模式,但转换却忽略了带有替换转换的自定义部分的存在。 ... [详细]
  • 基于Socket的多个客户端之间的聊天功能实现方法
    本文介绍了基于Socket的多个客户端之间实现聊天功能的方法,包括服务器端的实现和客户端的实现。服务器端通过每个用户的输出流向特定用户发送消息,而客户端通过输入流接收消息。同时,还介绍了相关的实体类和Socket的基本概念。 ... [详细]
  • 本文介绍了Oracle存储过程的基本语法和写法示例,同时还介绍了已命名的系统异常的产生原因。 ... [详细]
  • 本文详细介绍了cisco路由器IOS损坏时的恢复方法,包括进入ROMMON模式、设置IP地址、子网掩码、默认网关以及使用TFTP服务器传输IOS文件的步骤。 ... [详细]
  • centos安装Mysql的方法及步骤详解
    本文介绍了centos安装Mysql的两种方式:rpm方式和绿色方式安装,详细介绍了安装所需的软件包以及安装过程中的注意事项,包括检查是否安装成功的方法。通过本文,读者可以了解到在centos系统上如何正确安装Mysql。 ... [详细]
  • 本文介绍了解决Netty拆包粘包问题的一种方法——使用特殊结束符。在通讯过程中,客户端和服务器协商定义一个特殊的分隔符号,只要没有发送分隔符号,就代表一条数据没有结束。文章还提供了服务端的示例代码。 ... [详细]
  • 本文介绍了计算机网络的定义和通信流程,包括客户端编译文件、二进制转换、三层路由设备等。同时,还介绍了计算机网络中常用的关键词,如MAC地址和IP地址。 ... [详细]
author-avatar
yukiyu227232
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有