2011-12-22 14 views
7

मैं बहुत मुश्किल समय की कोशिश कर रहा webclientसी # WebClient लॉगिन accounts.google.com पर

का उपयोग कर रहा सी # WebClient वस्तु का उपयोग कर रहा है निम्न प्राप्त करने के लिए accounts.google.com पर प्रमाणित करने के लिए किया है।

service=oz 
dsh=-8355435623354577691 
GALX=33xq1Ma_CKI 
timeStmp= 
secTok= 
[email protected] 
Passwd=password 
signIn=Sign in 
PersistentCookie=yes 
rmShown=1 

अब प्रवेश पृष्ठ लोड होने से पहले मैं डेटा सबमिट जब यह है निम्न हेडर:

Content-Type    text/html; charset=UTF-8 
Strict-Transport-Security max-age=2592000; includeSubDomains 
Set-Cookie     GAPS=1:QClFh_dKle5DhcdGwmU3m6FiPqPoqw:SqdLB2u4P2oGjt_x;Path=/;Expires=Sat, 21-Dec-2013 07:31:40 GMT;Secure;HttpOnly 
Cache-Control    no-cache, no-store 
Pragma      no-cache 
Expires      Mon, 01-Jan-1990 00:00:00 GMT 
X-Frame-Options    Deny 
X-Auto-Login    realm=com.google&args=service%3Doz%26continue%3Dhttps%253A%252F%252Faccounts.google.com%252FManageAccount 
Content-Encoding   gzip 
Transfer-Encoding   chunked 
Date      Thu, 22 Dec 2011 07:31:40 GMT 
X-Content-Type-Options  nosniff 
X-XSS-Protection   1; mode=block 
Server      GSE 

ठीक

मैं https://accounts.google.com/ServiceLoginAuth?service=oz

यहाँ करने के लिए प्रपत्र फ़ील्ड्स प्रस्तुत करने कर रहा हूँ पोस्ट फ़ील्ड है अब मैं उन हेडर को शामिल करने के लिए वेब क्लाइंट क्लास का उपयोग कैसे करूं?

मैंने webClient_.Headers.Add(); पर प्रयास किया है लेकिन इसका सीमित प्रभाव है और हमेशा लॉगिन पृष्ठ लौटाता है।

नीचे एक कक्षा है जिसका मैं उपयोग करता हूं। किसी भी मदद की सराहना करेंगे।


हो रही प्रवेश पृष्ठ

public void LoginPageRequest(Account acc) 
    { 

     var rparams = new RequestParams(); 
     rparams.URL = @"https://accounts.google.com/ServiceLoginAuth?service=oz"; 
     rparams.RequestName = "LoginPage"; 
     rparams.Account = acc; 

     webClient_.DownloadDataAsync(new Uri(rparams.URL), rparams); 
    } 

    void webClient__DownloadDataCompleted(object sender, DownloadDataCompletedEventArgs e) 
    { 
     RequestParams rparams = (RequestParams)e.UserState; 

     if (rparams.RequestName == "LoginPage") 
     { 
      ParseLoginRequest(e.Result, e.UserState); 
     } 
    } 

अब हो रही प्रपत्र HtmlAgilityPack का उपयोग कर और उन्हें जोड़ने पैरामीटर संग्रह में खेतों

public void ParseLoginRequest(byte[] data, object UserState) 
    { 
     RequestParams rparams = (RequestParams)UserState; 

     rparams.ClearParams(); 

     ASCIIEncoding encoder = new ASCIIEncoding(); 

     string html = encoder.GetString(data); 

     HtmlNode.ElementsFlags.Remove("form"); 

     HtmlDocument doc = new HtmlDocument(); 
     doc.LoadHtml(html); 

     HtmlNode form = doc.GetElementbyId("gaia_loginform"); 

     rparams.URL = form.GetAttributeValue("action", string.Empty); 
     rparams.RequestName = "LoginPost"; 

     var inputs = form.Descendants("input"); 
     foreach (var element in inputs) 
     { 
      string name = element.GetAttributeValue("name", "undefined"); 
      string value = element.GetAttributeValue("value", ""); 
      if (!name.Equals("undefined")) { 

       if (name.ToLower().Equals("email")) 
       { 
        value = rparams.Account.Email; 
       } 
       else if (name.ToLower().Equals("passwd")) 
       { 
        value = rparams.Account.Password; 
       } 

       rparams.AddParam(name,value); 
       Console.WriteLine(name + "-" + value); 
      } 
     } 

     webClient_.UploadValuesAsync(new Uri(rparams.URL),"POST", rparams.GetParams,rparams); 

मैं डेटा पोस्ट करने के बाद मैं प्रवेश पृष्ठ के बजाय रीडायरेक्ट या सफलता प्राप्त संदेश।

मैं क्या गलत कर रहा हूं?

उत्तर

4

कुछ झुकाव के बाद, ऐसा लगता है कि वेब क्लाइंट क्लास इस विशेष समस्या का सबसे अच्छा तरीका नहीं है।

निम्नलिखित लक्ष्य प्राप्त करने के लिए मुझे नीचे एक स्तर को WebRequest पर कूदना पड़ा।

WebRequest करते समय (HttpWebRequest) और HttpWebResponse का उपयोग कर इसे CookieContainer

 webRequest_ = (HttpWebRequest)HttpWebRequest.Create(rparams.URL); 

     webRequest_.UserAgent = "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1; .NET CLR 1.1.4322; .NET CLR 2.0.50727)"; 
     CookieContainer cookieJar = new CookieContainer(); 
     webRequest_.CookieContainer = cookieJar; 

     string html = string.Empty; 

     try 
     { 
      using (WebResponse response = webRequest_.GetResponse()) 
      { 
       using (var streamReader = new StreamReader(response.GetResponseStream())) 
       { 
        html = streamReader.ReadToEnd(); 
        ParseLoginRequest(html, response,cookieJar); 
       } 
      } 
     } 
     catch (WebException e) 
     { 
      using (WebResponse response = e.Response) 
      { 
       HttpWebResponse httpResponse = (HttpWebResponse)response; 
       Console.WriteLine("Error code: {0}", httpResponse.StatusCode); 
       using (var streamReader = new StreamReader(response.GetResponseStream())) 
        Console.WriteLine(html = streamReader.ReadToEnd()); 
      } 
     } 

सेट करना संभव है और फिर जब पद ढंग

 webRequest_ = (HttpWebRequest)HttpWebRequest.Create(rparams.URL); 

     webRequest_.UserAgent = "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1; .NET CLR 1.1.4322; .NET CLR 2.0.50727)"; 
     webRequest_.Method = "POST"; 
     webRequest_.ContentType = "application/x-www-form-urlencoded"; 
     webRequest_.CookieContainer = cookieJar; 

     var parameters = new StringBuilder(); 

     foreach (var key in rparams.Params) 
     { 
      parameters.AppendFormat("{0}={1}&",HttpUtility.UrlEncode(key.ToString()), 
       HttpUtility.UrlEncode(rparams.Params[key.ToString()])); 
     } 

     parameters.Length -= 1; 

     using (var writer = new StreamWriter(webRequest_.GetRequestStream())) 
     { 
      writer.Write(parameters.ToString()); 
     } 

     string html = string.Empty; 

     using (response = webRequest_.GetResponse()) 
     { 
      using (var streamReader = new StreamReader(response.GetResponseStream())) 
      { 
       html = streamReader.ReadToEnd(); 

      } 
     } 

तो यह काम करता है निम्नलिखित में एक ही कुकी कंटेनर का उपयोग कर रही है, यह कोड उत्पादन के उपयोग के लिए नहीं है और इसे अनुकूलित/अनुकूलित किया जा सकता है। इसे एक उदाहरण के रूप में समझें।

+0

मैं इसे काम पर ला सकता हूं, क्या आप नमूना प्रोजेक्ट पोस्ट कर सकते हैं? – Smith

3

यह उत्तर फलक और अनचाहे में लिखा गया एक त्वरित उदाहरण है। फ़ॉर्मडाटा में जाने के लिए आपको कुछ फॉर्म मानों के प्रारंभिक अनुरोध से कुछ मानों को पार्स करने की आवश्यकता होगी। मेरा बहुत सी कोड इस प्रकार की प्रक्रिया पर आधारित है जब तक हमें फेसबुक स्पीडो टाइप साइट्स को स्क्रैप करने की आवश्यकता नहीं होती है, जिस स्थिति में AJAX हमें एक अलग दृष्टिकोण का उपयोग करता है।

using System; 
using System.Collections.Generic; 
using System.Collections.Specialized; 
using System.Linq; 
using System.Text; 

namespace GMailTest 
{ 
    class Program 
    { 
     private static NameValueCollection formData = new NameValueCollection(); 
     private static CookieAwareWebClient webClient = new CookieAwareWebClient(); 

     static void Main(string[] args) 
     { 
      formData.Clear(); 
      formData["service"] = "oz"; 
      formData["dsh"] = "-8355435623354577691"; 
      formData["GALX"] = "33xq1Ma_CKI"; 
      formData["timeStmp"] = ""; 
      formData["secTok"] = ""; 
      formData["Email"] = "[email protected]"; 
      formData["Passwd"] = "password"; 
      formData["signIn"] = "Sign in"; 
      formData["PersistentCookie"] = "yes"; 
      formData["rmShown"] = "1"; 

      byte[] responseBytes = webClient.UploadValues("https://accounts.google.com/ServiceLoginAuth?service=oz", "POST", formData); 
      string responseHTML = Encoding.UTF8.GetString(responseBytes); 
     } 
    } 

    public class CookieAwareWebClient : WebClient 
    { 
     public CookieAwareWebClient() : this(new CookieContainer()) 
     { } 

     public CookieAwareWebClient(CookieContainer c) 
     { 
      this.CookieContainer = c; 
      this.Headers.Add("User-Agent: Mozilla/5.0 (Windows NT 6.1) AppleWebKit/536.5 (KHTML, like Gecko) Chrome/19.0.1084.52 Safari/536.5"); 
     } 

     public CookieContainer CookieContainer { get; set; } 

     protected override WebRequest GetWebRequest(Uri address) 
     { 
      WebRequest request = base.GetWebRequest(address); 
      if (request is HttpWebRequest) 
      { 
       (request as HttpWebRequest).CookieContainer = this.CookieContainer; 
      } 
      return request; 
     } 
    } 
} 
+1

ऐसा लगता है कि रॉब उसी उद्योग में शामिल है जैसा मैं हूं, इस पोस्ट में उल्लेख किए गए कुछ AJAX aproaches पर चर्चा करने के लिए आपसे संपर्क करने के लिए उत्सुक रहना होगा – Tim

+0

आपको एक एफबी आमंत्रण भेजा गया –