在ASP.NET Web应用程序中隐藏queryString

时间:2008-09-19 08:09:49

标签: c# asp.net web-services

我有两个webapplication,一个是简单的authenticationsite,可以验证登录用户,重定向然后再到另一个站点。

因此我必须将userId(GUID)传递给第二个应用程序。目前这是通过URL完成的,但我想隐藏此ID。

有人知道如何正确地做到这一点吗?

[编辑]:由于ApplicationBoundaries(2个不同的服务器),我无法使用Session

8 个答案:

答案 0 :(得分:2)

这听起来像是一个棘手的情况。 但是,您可以使用多种选项,但这完全取决于您的应用程序的功能。

让我们将您的身份验证网站称为WebApp1,并在验证后将WebApp2称为您的目标网站。

WebApp2可以在幕后调用WebApp1吗? (服务)

在应用程序之间传递此Guid的问题是它是通过明文,并且考虑到它是用户ID,如果有人设法拦截它,他们将终身访问WebApp2。无论您是在查询字符串还是表单变量中传递它,它仍然容易受到攻击。

如果您无法使用WebApp2查询WebApp1,则应考虑WebApp1创建过期的临时Guid。从长远来看,这将更加安全,但由于明确的文字仍然容易受到攻击。这两个网络应用程序还需要访问同一个数据存储。

最终,我认为AU认证站点应该是WebApp2可以使用的服务。 用户应通过WebApp2登录,WebApp2将安全地调用WebApp1进行身份验证。 然后,WebApp2可以管理它自己的会话。

答案 1 :(得分:2)

如果你不能使用cookie,因为它是跨域的,那么用nonce加密它。

在两台服务器之间设置共享密钥/密钥;将加密的GUID和nonce组合发送到第二台服务器。 Unencrypt,检查nonce尚未使用(停止回复攻击),然后使用未加密的GUID。

如果你想要更加棘手的话,在app1上有一个web服务,它可以检查nonce是否实际发布(此时你正朝着WSTrust和单点登录解决方案,这通常可以解决你的问题试图做到)

即使使用Cookie,因为它们很容易编辑/伪造,您应该进行某种形式的检查。

答案 2 :(得分:2)

您有两个ASP.NET Web应用程序,一个应用程序除了对用户进行身份验证外什么都不做?

这听起来像是一份工作......

网络服务!

在身份验证应用上创建一个新的Web服务(它们是.asmx扩展名),并添加一个接收用户和密码等的方法,并返回身份验证信息。

然后在您的第二个应用程序上导入WSDL,并调用第一个应用程序,就像它是一个方法。它将简化您的代码并解决您的问题。

一个例子:

AuthenticateUserService.asmx进入身份验证应用程序:

using System;
using System.Web;
using System.Web.Services;
using System.Web.Services.Protocols;

[WebService(Namespace = "http://tempuri.org/")]
[WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)]
public class AuthenticateUserService : System.Web.Services.WebService 
{   
    [WebMethod]
    public bool AuthenticateUser(string username, string passhash) 
    {
        // Fake authentication for the example
        return (username == "jon" && passhash == "SomeHashedValueOfFoobar");
    }

}

设置完成后,启动主应用程序,右键单击该项目,然后单击“添加Web引用”。

在身份验证应用程序中输入asmx的URL,Visual Studio将发现它并创建代理类。

完成后,我们可以调用该方法,就像它是我们主应用程序中的本地方法一样:

protected void Page_Load(object sender, EventArgs e)
{
    // Now we can easily authenticate user in our code
    AuthenticateUserService authenticationProxy = 
         new AuthenticateUserService();
    bool isUserAuthenticated = 
         authenticationProxy.AuthenticateUser("jon", SomeHashMethod("foobar"));
}

那么,这到底是做什么的?

它从验证过程中消除了客户端。

您当前的流程:

  • 客户端向AppA输入凭据
  • AppA将客户端重定向到AppB
  • 如果凭据匹配,AppB会将客户端重定向回AppA。

替换为AppA和AppB之间的服务器端SOAP调用。现在它是这样的:

  • 客户在AppA中输入凭据
  • AppA询问AppB是否合适
  • AppA向客户提供适当的内容。

答案 3 :(得分:0)

以最佳方式通过会话传递GUID。

http://www.w3schools.com/ASP/asp_sessions.asp

或者,因为它是2个不同的服务器,所以通过POST方法传递信息:

http://www.w3schools.com/aspnet/aspnet_forms.asp

另一种可能性是将会话状态存储在本地服务器上的数据库中,并从另一台服务器远程访问该数据库,以查看用户是否已成功登录并在会话时限内。

考虑到这一点,您也可以远程执行整个身份验证。从远程服务器远程连接到本地数据库并从那里检查登录凭据......这样您就可以将会话和/或cookie存储在远程服务器上。

我建议反对隐藏的字段命题,因为它完全抵消了你想要做的事情!您试图隐藏URL中的GUID,但在HTML代码中发布相同的信息!这不是这样做的方法。

最佳选择是数据库选项,如果不可能,则使用HTTP POST。

答案 4 :(得分:0)

使用会话变量或HTTP POST而不是HTTP GET。

答案 5 :(得分:0)

如果服务器具有通用域名,则可以使用cookie。

编辑:Cookie只会在视觉上隐藏ID,但仍然可以访问。与隐藏字段相同或使用POST而不是GET。因此,如果该ID具有信心并且您希望避免通过未加密的网络发送它,则需要采用不同的方法。

解决方案可以是使用服务器共享的密钥加密auth服务器上的ID。另一种解决方案是在auth服务器上生成随机GUID,然后让auth服务器直接通知其他服务器(通过SSL)GUID对应的ID。

答案 6 :(得分:0)

不是通过查询字符串传递它,而是应该创建一个隐藏的表单字段及其值,然后发布到第二页,然后可以获取已发布的值,并且它将对用户隐藏。

答案 7 :(得分:0)

进行会话管理或使用HTTP帖子,如上文所述。