c#实现单点登陆

原理:客户访问我的超链接,传来一个key值,我通过这个key‘值去客户的esb系统去验证,若验证成功,返回用户信息,我拿到用户信息,跟本地服务器的用户信息进行比对,若一致,跳过登陆页面,直接授权进入系统。客户是内网,域名又有限制,访问不到接口,只能进行远程调试;因为获取用户用的是soap协议,所以还需要生成wsdl文件的代理类。

主要代码如下:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Configuration;
using System.Security.Cryptography;
using TechExcel.Project.DataAccess;
using TechExcel.Project.DataAccess.Service;
using TechExcel.Project.DataAccess.Utility;
using System.Net;
using System.Net.Security;
using System.Security.Cryptography.X509Certificates;
using System.Text;
using System.IO;
using System.Xml;
using TechExcel.PPM.ProjectWeb.WebServiceEastHope;

namespace TechExcel.PPM.ProjectWeb
{
    public partial class SSOLogin4EastHope : System.Web.UI.Page
    {
        protected void Page_Load(object sender, EventArgs e)
        {
            CookieContainer cookieContainer = new CookieContainer();
            string url = ConfigurationManager.AppSettings.Get("EastHopeEsbUrl");//esb接口的url
            string strUser= string.Empty;//用户信息
            string token = string.Empty;//key值
            string iPlanetDirectoryProVal = string.Empty;//
            int timeout = 0;
            string userAgent = string.Empty;
            string strLang = string.Empty;
            int nLangID = 0;
            int.TryParse(strLang, out nLangID);
            string strRuntimeKey = string.Empty;         
            if (Request.Cookies == null)
            {
                Response.Write("cookie is null");
                //Response.Redirect("login.aspx");
                return;
            }
            if (HttpContext.Current.Request.Cookies["tokenID"] != null)
            {
                iPlanetDirectoryProVal = HttpContext.Current.Request.Cookies["tokenID"].Value;
            }
            if (HttpContext.Current.Request.Cookies["iPlanetDirectoryPro"] != null)
            {
              
                string tokenTemp = HttpContext.Current.Request.Cookies["iPlanetDirectoryPro"].Value;
                Response.Write("iPlanetDirectoryPro is not null " + tokenTemp);
                string xmlToken=GetXml(tokenTemp);
                //拿到cookies的key值并且生成xml数据的格式之后,到ESB系统获取用户信息
                //Cookie cookie = new Cookie("tokenID", tokenTemp);
                //HttpHelper httpR = new HttpHelper();
                //HttpWebResponse re = httpR.CreateGetHttpResponse(url, timeout, userAgent, cookie,xmlToken);
                AuthenticationWSClient authticayion=new AuthenticationWSClient();
                string xmlIn=authticayion.getTokenUser(xmlToken);
                if (xmlIn != null)
                {
                    //string xmlIn = new StreamReader(re.GetResponseStream(), Encoding.UTF8).ReadToEnd();
                    strUser = getXmlUser(xmlIn);
                    Response.Write("xmlIn is not null " + xmlToken +  "  xmlIn:"+xmlIn+" strUser:"+strUser);
                    if (strUser != null)
                    {
                        if (SSOAuthentication(nLangID, strRuntimeKey, strUser))
                            return;
                    }
                }
                else
                {
                    Response.Write("re is null "+xmlToken);
                }
            }
            Response.Write(" token is null");
            //Response.Redirect("login.aspx");
            Response.End();
        }
        public string GetXml(string tokenID)//要发送的XML
        {
            StringBuilder strBuilder = new StringBuilder();
            strBuilder.Append("");
            //strBuilder.Append("");
            //strBuilder.Append(" ");
            //strBuilder.Append("");
           // strBuilder.Append(" ");
            //strBuilder.Append(" ");
            strBuilder.Append("");
            strBuilder.Append("");
            strBuilder.Append(tokenID);
            strBuilder.Append("");
            strBuilder.Append("");
            //strBuilder.Append("");
            //strBuilder.Append("");
           // strBuilder.Append("");
            //strBuilder.Append("");
            return strBuilder.ToString();
        }
        private string getXmlUser(string xml)  
        {  
            XmlDocument xmlDoc = new XmlDocument();            
            try  
            {  
                xmlDoc.LoadXml(xml);                 
                XmlNodeList xnList = xmlDoc.SelectNodes("//ESBMessage/DATA/ITEM");  
                Console.WriteLine("共有{0}个节点", xnList.Count);//输出xnList中节点个数。  
                foreach (XmlNode xn in xnList)  
                {  
                    //无法使用xn["ActivityId"].InnerText  
                    string userIF = (xn.SelectSingleNode("USERID")).InnerText;
                    return userIF;
                }  
            }  
            catch (Exception e)  
            {   
                Console.WriteLine(e.Message);  
            }
            return null;
        }  
        private bool SSOAuthentication(int languageID, string runtimeKey, string ssoKey)
        {
            string client = Request.UserHostAddress;//获取用户的客户端的主机地址
            try
            {
                //? SSOHelper
                TechExcel.SSO.ISSOHandle ssoHandler = SSOHelper.GetSSOHandle();
                if (ssoHandler != null)
                {
                    //验证用户是否存在我们的数据库中
                    TechExcel.SSO.ValidateResult result = ssoHandler.ValidateTicket(ssoKey);
                    if (result.Code == 1)
                    {
                        //定义url,usernam两个变量接收他们的值
                        string url = String.Empty;
                        string userName = result.Username;
                        int enableValidateClientIP = 0;
                        int.TryParse(ConfigurationManager.AppSettings["EnableValidateClientIP"], out enableValidateClientIP);
                        //Response.Redirect(GetFriendlyUrl('terry-j', 78, 0), false);
                        
                        SystemDataHandler handler = new SystemDataHandler();
                        //TUserLoginData data = handler.UserSSOLoginEx(client, userName, languageID, enableValidateClientIP);
                        TUserLoginData data = handler.UserSSOLoginEx(client, userName, languageID, enableValidateClientIP);
                        if (data != null)//如果data不为null,表示授权成功,并成功跳过登陆界面
                        {
                            //给客户端设置session的值
                            SetSessionValue(data.UserID, data.SessionID, 0, languageID);
                            //如果runtime存在的话,就加上runtime的后缀,如果runtime没有值,那就不设置后缀
                            if (runtimeKey == "")
                            {
                                url = "ProjectFrame.aspx";
                            }
                            else
                            {
                                url = string.Format("ProjectFrame.aspx?RuntimeKey={0}", runtimeKey);
                            }
                            Response.Redirect(GetFriendlyUrl(data.UserID, data.SessionID, languageID), false);
                            return true;
                        }
                         
                    }
                    else
                    {
                        string strLoginurl = ssoHandler.GetLoginUrl();
                        Response.Redirect("login.aspx");
                        Response.End();
                    }
                }
            }
            catch
            {
            }

            return false;
        }

        private string GetFriendlyUrl(int userID, int SessionID, int languageID)
        {
            TTabSetting setting = UserPreferenceService.GetUserTabSetting(userID, SessionID, languageID);
            string selectedHash = setting.SelectedTabHash;

            return "#" + selectedHash.Trim(new char[] { ' ', '#' });
        }

        private void SetSessionValue(int userid, int sessionid, int ldapid, int languageid)
        {
            //获取客户端的主机地址
            string client = Request.UserHostAddress;
            //然后将他们转化为一个字符串对象的形式
            string data = string.Format("{0}&{1}&{2}&{3}&{4}&{5}", userid, sessionid, ldapid, languageid, client, DateTime.Now.Ticks);
            //以下在返回的reposnse中创建三个cookies
            HttpCookie cookie = Response.Cookies["DevSuiteWebUserData"];
            cookie.Expires = DateTime.Now.AddYears(1);//设置cookies的超时时间为一年,不设置的话,默认值是session,就是将和session一起失效
            cookie.HttpOnly = true;//设置js脚本禁止读取cookies的信息,这样有效防止了cookie被人攻击,提高安全性
            cookie.Secure = Request.IsSecureConnection;//secure属性可防止信息在传递的过程中被监听捕获后导致信息泄露,如果设置为true,可以限制只有通过https访问时,才会将浏览器保存的cookie传递到服务端,如果通过http访问,不会传递cookie。
            cookie.Value = DESHelper.EncryptData(data);//将cookies进行加密

            cookie = Response.Cookies["txdevtrackltmsid"];
            cookie.Expires = DateTime.Now.AddYears(1);
            cookie.HttpOnly = true;
            cookie.Secure = Request.IsSecureConnection;
            cookie.Value = DESHelper.EncryptData_DevTrack(string.Format("{0}", sessionid));//

            cookie = Response.Cookies["DSCSID"];
            cookie.Expires = DateTime.Now.AddYears(1);
            cookie.HttpOnly = true;
            cookie.Secure = Request.IsSecureConnection;
            cookie.Value = DESHelper.EncryptData_DevSpec(string.Format("{0}&{1}", sessionid, userid));

        }
    }
    ///  
    /// 创建GET方式的HTTP请求 
    ///  
    ///
    public class HttpHelper
    {
        public HttpWebResponse CreateGetHttpResponse(string url, int timeout, string userAgent,Cookie cookie,string xmlToken)
        {
            if (string.IsNullOrEmpty(url))
            {
                throw new ArgumentNullException("url");
            }
            HttpWebRequest request = null;
            HttpWebResponse res;
            request = WebRequest.Create(url) as HttpWebRequest;
            request.Method = "POST";
            request.ContentType = "text/xml";
            request.Headers.Add("charset:utf-8");
            if (xmlToken != null)
            {
                var encoding = Encoding.GetEncoding("utf-8");
                byte[] buffer = encoding.GetBytes(xmlToken);
                request.ContentLength = buffer.Length;
                request.GetRequestStream().Write(buffer, 0, buffer.Length);
            }
            if(false)
            {
                try
                {
                    request.CookieContainer = new CookieContainer();
                    request.CookieContainer.Add(cookie);
                }
                catch (CookieException ex)      
                {
                    
                }
            }
            //设置代理UserAgent和超时
            //request.UserAgent = userAgent;
            //request.Timeout = timeout;
            try
            {
                res = (HttpWebResponse)request.GetResponse();
                return res;
            }
            catch (WebException ex)
            {
                res = (HttpWebResponse)ex.Response;
            }
            return res;
        }
    }
}

因为写完代码不能直接就发布,我这边是自己模拟了客户的后台环境进行了简单的测试,当然这个测试没有利用soap协议,是post的http方式。代码如下:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Configuration;
using System.Security.Cryptography;
using System.Net;
using System.Net.Security;
using System.Security.Cryptography.X509Certificates;
using System.Text;
using System.IO;
using System.Xml;
namespace WebApplication1
{
    public partial class WebForm1 : System.Web.UI.Page
    {
        protected void Page_Load(object sender, EventArgs e)
        {
            if (getXmlUser() == "13jklj")
            {
                string xmlRepon = GetXml("terry-j");
                Response.ContentType = "text/xml";
                Response.Write(xmlRepon.ToString());
                Response.End();
            }
        }
        public XmlDocument GetDataSet()
        {
            try
            {
                Stream inputstream = Request.InputStream;
                byte[] b = new byte[inputstream.Length];
                inputstream.Read(b, 0, (int)inputstream.Length);
                string inputstr = UTF8Encoding.UTF8.GetString(b);
                XmlDocument d = new XmlDocument();
                d.LoadXml(inputstr);
                return d;
            }
            catch
            {

            }
            return null;
        }
        public string GetXml(string tokenID)//要发送的XML
        {
            StringBuilder strBuilder = new StringBuilder();
            strBuilder.Append("");
            strBuilder.Append("");
            strBuilder.Append("");
            strBuilder.Append("");
            strBuilder.Append("");
            strBuilder.Append(tokenID);
            strBuilder.Append("");
            strBuilder.Append("");
            strBuilder.Append("");
            strBuilder.Append("");
            return strBuilder.ToString();
        }
        private string getXmlUser()
        {
            XmlDocument xmlDoc = GetDataSet();
            try
            {
                XmlNodeList xnList = xmlDoc.SelectNodes("//params");
                Console.WriteLine("共有{0}个节点", xnList.Count);//输出xnList中节点个数。  
                foreach (XmlNode xn in xnList)
                {
                    //无法使用xn["ActivityId"].InnerText  
                    string userIF = (xn.SelectSingleNode("tokenID")).InnerText;
                    return userIF;
                }
            }
            catch (Exception e)
            {
                Console.WriteLine(e.Message);
            }
            return null;
        }
    }
}

 

你可能感兴趣的:(c#开发)