安全单点登录 ASP.NET,用于通过 OpenID 从其他 (php) 网站进行身份验证


Secure Single Sign On in ASP.NET for the authentication from anthother (php) website via OpenID

我需要在我的 asp.net 上实现以下身份验证:ASP.NET 和PHP网站上的用户应该使用OpenID进行身份验证。登录和注册仅存在于PHP网站上。所以要求是:

  • 我的 ASP.NET 网站应重定向到 PHP 网站进行身份验证。用户将使用 PHP 网站上的 OpenID 进行身份验证。
  • 如果用户是新用户(我打算使用coookie)到我的 ASP.NET 网站,它将重定向为空参数。否则,我会在重定向请求中传递存储的 OpenID。
  • 如果传递的 OpenID 为空,PHP 网站将向用户显示登录页面,并允许用户进行身份验证和注册自己。如果传递的 OpenID 不为空。PHP 网站应检查其有效状态。
  • 只有当身份验证/注册成功时,PHP 网站才会重定向回我的 ASP.NET 网站 OpenID,我将用于用户。
  • 当然,这个过程必须是安全的。

我发现身份验证检查应该在 Global.asax 中使用 FormAuthentication Application_AuthenticateRequest 事件中实现。我这样计划着

protected void Application_AuthenticateRequest(Object sender, EventArgs e) {
  if(HttpContext.Current.User != null) {
    // Extract the forms authentication cookie if exists.
    // Redirects to the php website using the OpenID extracted from the cookies, or empty.
    // Pass also a new generated token to secure the communication.
  } else {
    // Store a new GeneralPrincipal to the HttpContext.Current.User.
  }
}
protected void Application_BeginRequest(Object sender, EventArgs e) {
  // Check for the redirected back token and OpenID.
  // Create FormsAuthenticationTicket for the openid and store it in the cookie.
}

问题是,我无法将生成的令牌保存在会话中,因为当时未初始化会话状态。

解决上述要求的最佳实践是什么?

我已经

通过对所有应该受到保护的网站使用基页类来解决这个问题。用户将在 OnInit 中检查每个请求,如下所示

protected override void OnInit(EventArgs e) {
// Check Identity.
if(HttpContext.Current.User.Identity.IsAuthenticated) {
  // The user is already authenticated.
  // Get the user...
  return;    
}
// Check if the php server sends request with token.
if(!string.IsNullOrEmpty(Request.QueryString["token"])) {
  try {
    // Get user from the PHP-Server by the token.
    //...
    // Remove old FormsAuthentication.
    FormsAuthentication.SignOut();
    // Save new authentication.
    SaveAuthentication();
  } catch(Exception exception) {
    // Handle...
    return;
  }
} else {
   // Get new php-token and redirect to the php-server for the authentication.
   //...
}

对于可本地化的 ASP.NET 网站,可以在 InitializeCulture 方法中实现。