HttpWebRequest:如何通过带有x-www-form-enclosed的WebRequest在Canada Post找到邮政编码?

我目前正在编写一些测试,以便通过Windows Forms进行Internet交互来提高我的技能。 其中一项测试是查找加拿大邮政网站应返回的邮政编码。

  1. 我的默认url设置为: http : //www.canadapost.ca/cpotools/apps/fpc/personal/findByCity?execution=e4s1
  2. 所需的表单字段是: streetNumberstreetNamecityprovince
  3. contentType是“application / x-www-form-enclosed”

编辑:请考虑值“application / x-www-form-encoded”而不是point 3值作为contentType。 (感谢EricLaw-MSFT!)

我得到的结果不是预期的结果。 我得到了页面的HTML源代码,我可以手动输入信息来查找邮政编码,但不能找到带有找到的邮政编码的HTML源代码。 我知道我做错了什么?

我应该考虑采用XML方式吗? 首先是匿名搜索加拿大邮政吗?

这是一个代码示例,以便更好地描述:

public static string FindPostalCode(ICanadadianAddress address) { var postData = string.Concat(string.Format("&streetNumber={0}", address.StreetNumber) , string.Format("&streetName={0}", address.StreetName) , string.Format("&city={0}", address.City) , string.Format("&province={0}", address.Province)); var encoding = new ASCIIEncoding(); byte[] postDataBytes = encoding.GetBytes(postData); request = (HttpWebRequest)WebRequest.Create(DefaultUrlSettings); request.ImpersonationLevel = System.Security.Principal.TokenImpersonationLevel.Anonymous; request.Container = new CookieContainer(); request.Timeout = 10000; request.ContentType = contentType; request.ContentLength = postDataBytes.LongLength; request.Method = @"post"; var senderStream = new StreamWriter(request.GetRequestStream()); senderStream.Write(postDataBytes, 0, postDataBytes.Length); senderStream.Close(); string htmlResponse = new StreamReader(request.GetResponse().GetResponseStream()).ReadToEnd(); return processedResult(htmlResponse); // Processing the HTML source code parsing, etc. } 

在我的观点中,我似乎陷入瓶颈。 我找不到想要的结果。

编辑:似乎有这个网站的ContentType参数。 让我解释。

  • 有一个“元”变量,规定如下:

meta http-equiv =“Content-Type”content =“application / xhtml + xml,text / xml,text / html; charset = utf-8”

  • 另一个后来的代码被读作:

form id =“fpcByAdvancedSearch:fpcSearch”name =“fpcByAdvancedSearch:fpcSearch”method =“post”action =“/ cpotools / apps / fpc / personal / findByCity?execution = e1s1”enctype =“application / x-www-form-urlencoded “

我的问题如下:我必须坚持哪一个?

让我猜一下,第一个ContentType被认为是第二个仅用于发布数据时对函数的另一个请求?

编辑:根据请求,我更接近解决方案列在这个问题下: WebRequest:如何使用WebRequest查找邮件代码对此ContentType =“application / xhtml + xml,text / xml,text / html; 字符集= UTF-8” ?

谢谢你的帮助! 🙂

我试图找出你没有使用WebClient类的原因: –

 var fields = new NameValueCollection(); fields.Add("streetnumber", address.StreetNumber); fields.Add("streetname", address.StreetName); fields.Add("city", address.City); fields.Add("province", address.Province); var wc = new WebClient(); byte[] resultData = wc.UploadValues(url, fields); string result = Encoding.Default.GetString(resultData); 

您可能希望在发送结果时检查服务器使用的编码,如果它使用UTF-8将最后一行更改为: –

 string result = Encoding.UTF8.GetString(resultData); 

我在您的原始代码中发现的一些问题: –

  1. 第一个字段以&为前缀,不应该在那里。
  2. 您需要在每个字段值上调用Uri.EscapeDataString
  3. 您正在尝试围绕GetRequestStream的结果构造一个内存流,即使MemoryStream有这样的构造函数,我也看不到它会实现什么,但它无论如何都没有。 只需直接写入GetRequestStream返回的流

如果你已经这样做了,那就给自己一个fiddler的副本,这样你就可以观察到标准表单成功请求数据以及你的代码在做什么时会发生什么。

编辑 :如果您有证据表明缺少cookie容器导致WebClient无法工作,那么您可以尝试这种方法: –

 public class MyWebClient : WebClient { protected override WebRequest GetWebRequest (Uri address) { WebRequest request = (WebRequest) base.GetWebRequest (address); request.Container = new CookieContainer(); return request; } } 

现在使用上面的代码,而不是实例化WebClient实例MyWebClient

HTTPWebRequest将返回URLrequested的内容。 如果是HTML页面,它将返回HTML标记。 如果页面内容是XML,则它将返回XML标记。

听起来你需要的是Web服务。 我会看看该网站是否有任何可用于处理该类型请求的webserivces。 如果他们这样做,那么它将返回XML,JSON标记以响应您的查询。 否则,您将解析请求的输出。