从非Web客户端调用ASP.NET 2.0身份验证服务

时间:2010-08-12 14:46:40

标签: asp.net web-services authentication .net-2.0

我正在研究一个调用ASP.NET 2.0网站的.NET 2.0 winforms应用程序。该网站使用表单身份验证进行身份验证。在web.config中启用了身份验证服务,我已经完成了一些experiments以确认我可以通过JSON访问该服务。

这是我的问题:是否有任何内置代码在纯.NET环境(而不是ASP.NET)中使用System.Web.Extensions Web服务(authenticationService,profileService等)?我可以找到使用Silverlight和后来的WCF服务的示例,但在客户端和服务器上的2.0环境中都找不到任何示例。将身份验证服务添加为Web服务似乎是合乎逻辑的方法,但我无法让它指向我的开发服务器 - 我想这可能是一个单独的问题。

如果我必须在较低级别管理AJAX请求和响应,那肯定是可行的,但是如果某些内容已经用于此目的,那肯定会更容易,也不会出错。

2 个答案:

答案 0 :(得分:1)

我从来没有得到过这方面的答案,但最终在this tutorial的帮助下找到了答案。简短的回答是肯定的,我必须在相当低的水平上管理AJAX请求/响应。假设您需要使用用户名和密码进行身份验证,首先需要获取身份验证cookie。我使用Json.NET library from Newtonsoft进行JSON序列化和反序列化,但你可以使用任何东西。

Cookie GetFormAuthenticationCookie(string username, string password)
        {
            string uriString = ServerName + AUTH_SERVICE_URL;
            Uri uri = new Uri(uriString);

            // Need to cast this to HttpWebRequest to set CookieContainer property
            // With a null CookieContainer property on the request, we'd get an
            // empty HttpWebRequest.Cookies property
            HttpWebRequest request = WebRequest.Create(uri) as HttpWebRequest;
            request.Method = "POST";
            request.ContentType = "application/json; charset=utf-8";
            request.CookieContainer = new CookieContainer(); // needed to get non-empty Cookies collection back in response object

            // requestContents needs to look like this:
            // {
            //     username = 'theUserName',
            //     password = 'thePassword',
            //     createPersistentCookie = false
            // }
            string requestContents = GetJsonForLoginRequest(username, password);

            byte[] postData = Encoding.UTF8.GetBytes(requestContents);
            request.ContentLength = postData.Length;
            using (Stream dataStream = request.GetRequestStream())
            {
                dataStream.Write(postData, 0, postData.Length);
            }

            HttpWebResponse response = (HttpWebResponse)request.GetResponse();
            if (response.StatusCode != HttpStatusCode.OK)
            {
                throw new WebException("Response returned HttpStatusCode " + response.StatusCode);
            }

            // For now, assuming response ContentType is "application/json; charset=utf-8"
            object responseJson;
            using (Stream responseStream = response.GetResponseStream())
            {
                StreamReader reader = new StreamReader(responseStream);
                string responseString = reader.ReadToEnd();

                responseJson = JavaScriptConvert.DeserializeJson(responseString);
            }

            if (responseJson is bool)
            {
                bool authenticated = (bool)responseJson;
                if (authenticated)
                {
                    // response was "true"; return the cookie
                    return response.Cookies[".ASPXFORMSAUTH"];
                }
                else
                {
                    // apparently the login failed
                    return null;
                }
            }
            else
            {
                return null;
            }
        }

接下来,将cookie添加到后续请求中。就我而言,这意味着将cookie添加到我正在使用的Web服务代理的CookieContainer中。

答案 1 :(得分:0)

我无法使authenticationService正常工作。当我尝试从winforms应用程序调用Authentication_JSON_AppService.axd时,我一直收到404错误。所以我最终编写了自己的JSON身份验证WebMethod。

抱歉,这不是C#,我的项目是VB.NET。我使用此http://progtutorials.tripod.com/Authen.htm作为参考。

<WebMethod(EnableSession:=True)>
<ScriptMethod(ResponseFormat:=ResponseFormat.Json)>
Public Function Login(ByVal username As String, ByVal password As String) As Boolean

    Dim result As Boolean = False

    ' If (FormsAuthentication.Authenticate(username,password)) ' this may also work to authenticate
    If (Membership.ValidateUser(username, password)) Then 
        FormsAuthentication.SetAuthCookie(username, False)

        Dim ticket As FormsAuthenticationTicket = New FormsAuthenticationTicket(username, False, 30)
        Dim ticketString As String = FormsAuthentication.Encrypt(ticket)

        Dim cookie As HttpCookie = New HttpCookie(FormsAuthentication.FormsCookieName, ticketString)
        Context.Response.Cookies.Add(cookie)

        result = True

    End If

    Return result

End Function

请确保您的身份验证WebService可供web.config中的匿名用户访问。

  <location path="Authentication.asmx">
    <system.web>
      <authorization>
        <allow users="*" />
      </authorization>
    </system.web>
  </location>