我举了一个例子,用另一个问题在C#中填写表单,但是当我运行代码时,我只是再次返回页面(好像我没有提交任何内容)。我尝试手动转到网址并添加了?variable=value&variable2=value2
,但这似乎没有预先填充表单,不确定这是不是为什么这不起作用。
private void button2_Click(object sender, EventArgs e)
{
var encoding = new ASCIIEncoding();
var postData = "appid=001";
postData += ("&email=chris@test.com");
postData += ("&receipt=testing");
postData += ("&machineid=219481142226.1");
byte[] data = encoding.GetBytes(postData);
var myRequest =
(HttpWebRequest)WebRequest.Create("http://www.example.com/licensing/check.php");
myRequest.Method = "POST";
myRequest.ContentType = "application/x-www-form-urlencoded";
myRequest.ContentLength = data.Length;
var newStream = myRequest.GetRequestStream();
newStream.Write(data, 0, data.Length);
newStream.Close();
var response = myRequest.GetResponse();
var responseStream = response.GetResponseStream();
var responseReader = new StreamReader(responseStream);
label2.Text = responseReader.ReadToEnd();
}
答案 0 :(得分:5)
要以编程方式提交表单,一般的想法是您要模拟浏览器。为此,您需要找到URL,HTTP标头和POST数据的正确组合以满足服务器的要求。
了解服务器需求的最简单方法是使用Fiddler,FireBug或其他工具,它可以让您准确检查浏览器通过网络发送的内容。然后,您可以通过添加或删除标头,更改POST数据等来试验您的代码,直到服务器接受请求为止。
以下是您可能遇到的一些问题:
@
字符编码为%40
也可能存在其他挑战,但上述情况最有可能发生。要查看完整列表,请查看my answer到另一个屏幕抓取问题。
顺便说一句,您用来提交表单的代码比需要的代码更难和更冗长。相反,您可以使用WebClient.UploadValues()
并使用更少的代码完成相同的操作,并自动为您完成编码。像这样:
NameValueCollection postData = new NameValueCollection();
postData.Add ("appid","001");
postData.Add ("email","chris@test.com");
postData.Add ("receipt","testing");
postData.Add ("machineid","219481142226.1");
postData.Add ("checkit","checkit");
WebClient wc = new WebClient();
byte[] results = wc.UploadValues (
"http://www.example.com/licensing/check.php",
postData);
label2.Text = Encoding.ASCII.GetString(results);
更新:
鉴于我们在评论中的讨论,您遇到的问题是我最初提到的原因之一:
表单可能正在检查会话cookie或身份验证 cookie,意味着你需要提出一个请求(拿起 cookie)然后做出随后提出的提交表格的请求。
在使用Cookie进行会话跟踪或身份验证的服务器上,如果请求显示没有附加cookie,则服务器通常会重定向到相同的URL。重定向将包含Set-Cookie
标头,这意味着当重新请求重定向的URL时,它将具有客户端附加的cookie。如果第一个请求是表单POST,则此方法会中断,因为服务器和/或客户端不处理POST的重定向。
正如我最初描述的那样,修复程序是初始GET请求以获取cookie,然后将POST作为第二个请求,并传回cookie。
像这样:
using System;
public class CookieAwareWebClient : System.Net.WebClient
{
private System.Net.CookieContainer Cookies = new System.Net.CookieContainer();
protected override System.Net.WebRequest GetWebRequest(Uri address)
{
System.Net.WebRequest request = base.GetWebRequest(address);
if (request is System.Net.HttpWebRequest)
{
var hwr = request as System.Net.HttpWebRequest;
hwr.CookieContainer = Cookies;
}
return request;
}
}
class Program
{
static void Main(string[] args)
{
var postData = new System.Collections.Specialized.NameValueCollection();
postData.Add("appid", "001");
postData.Add("email", "chris@test.com");
postData.Add("receipt", "testing");
postData.Add("machineid", "219481142226.1");
postData.Add("checkit","checkit");
var wc = new CookieAwareWebClient();
string url = "http://www.example.com/licensing/check.php";
// visit the page once to get the cookie attached to this session.
// PHP will redirect the request to ensure that the cookie is attached
wc.DownloadString(url);
// now that we have a valid session cookie, upload the form data
byte[] results = wc.UploadValues(url, postData);
string text = System.Text.Encoding.ASCII.GetString(results);
Console.WriteLine(text);
}
}