【发布时间】:2011-07-21 01:34:23
【问题描述】:
我需要使用带有 WebClient 的“HTTP Post”将一些数据发布到我拥有的特定 URL。
现在,我知道这可以通过 WebRequest 来完成,但由于某些原因,我想改用 WebClient。那可能吗?如果是这样,有人可以给我一些例子或指出正确的方向吗?
【问题讨论】:
我需要使用带有 WebClient 的“HTTP Post”将一些数据发布到我拥有的特定 URL。
现在,我知道这可以通过 WebRequest 来完成,但由于某些原因,我想改用 WebClient。那可能吗?如果是这样,有人可以给我一些例子或指出正确的方向吗?
【问题讨论】:
我刚刚找到了解决方案,是的,它比我想象的要容易:)
所以这里是解决方案:
string URI = "http://www.myurl.com/post.php";
string myParameters = "param1=value1¶m2=value2¶m3=value3";
using (WebClient wc = new WebClient())
{
wc.Headers[HttpRequestHeader.ContentType] = "application/x-www-form-urlencoded";
string HtmlResult = wc.UploadString(URI, myParameters);
}
它的作用就像魅力:)
【讨论】:
HttpRequestHeader.ContentType枚举成员web.Headers[HttpRequestHeader.ContentType]:p
WebClient 继承自 Component,其中包含 ~Component() {Dispose(false);})。问题是垃圾收集器可能需要任意长的时间才能这样做,因为它在做出收集决定时没有考虑非托管资源。必须尽快清理高价值资源。例如,打开不需要的文件句柄可能会阻止文件被其他代码删除或写入。
有一个名为UploadValues 的内置方法可以发送 HTTP POST(或任何类型的 HTTP 方法)并以正确的形式处理请求正文的构造(使用“&”连接参数并通过 url 编码转义字符)数据格式:
using(WebClient client = new WebClient())
{
var reqparm = new System.Collections.Specialized.NameValueCollection();
reqparm.Add("param1", "<any> kinds & of = ? strings");
reqparm.Add("param2", "escaping is already handled");
byte[] responsebytes = client.UploadValues("http://localhost", "POST", reqparm);
string responsebody = Encoding.UTF8.GetString(responsebytes);
}
【讨论】:
使用WebClient.UploadString 或WebClient.UploadData,您可以轻松地将数据发布到服务器。我将展示一个使用 UploadData 的示例,因为 UploadString 的使用方式与 DownloadString 相同。
byte[] bret = client.UploadData("http://www.website.com/post.php", "POST",
System.Text.Encoding.ASCII.GetBytes("field1=value1&field2=value2") );
string sret = System.Text.Encoding.ASCII.GetString(bret);
【讨论】:
string URI = "site.com/mail.php";
using (WebClient client = new WebClient())
{
System.Collections.Specialized.NameValueCollection postData =
new System.Collections.Specialized.NameValueCollection()
{
{ "to", emailTo },
{ "subject", currentSubject },
{ "body", currentBody }
};
string pagesource = Encoding.UTF8.GetString(client.UploadValues(URI, postData));
}
【讨论】:
//Making a POST request using WebClient.
Function()
{
WebClient wc = new WebClient();
var URI = new Uri("http://your_uri_goes_here");
//If any encoding is needed.
wc.Headers["Content-Type"] = "application/x-www-form-urlencoded";
//Or any other encoding type.
//If any key needed
wc.Headers["KEY"] = "Your_Key_Goes_Here";
wc.UploadStringCompleted +=
new UploadStringCompletedEventHandler(wc_UploadStringCompleted);
wc.UploadStringAsync(URI,"POST","Data_To_Be_sent");
}
void wc__UploadStringCompleted(object sender, UploadStringCompletedEventArgs e)
{
try
{
MessageBox.Show(e.Result);
//e.result fetches you the response against your POST request.
}
catch(Exception exc)
{
MessageBox.Show(exc.ToString());
}
}
【讨论】:
使用简单的client.UploadString(adress, content); 通常可以正常工作,但我认为应该记住,如果没有返回 HTTP 成功状态代码,则会抛出 WebException。我通常这样处理它以打印远程服务器返回的任何异常消息:
try
{
postResult = client.UploadString(address, content);
}
catch (WebException ex)
{
String responseFromServer = ex.Message.ToString() + " ";
if (ex.Response != null)
{
using (WebResponse response = ex.Response)
{
Stream dataRs = response.GetResponseStream();
using (StreamReader reader = new StreamReader(dataRs))
{
responseFromServer += reader.ReadToEnd();
_log.Error("Server Response: " + responseFromServer);
}
}
}
throw;
}
【讨论】:
使用带有模型的webapiclient发送序列化json参数请求。
PostModel.cs
public string Id { get; set; }
public string Name { get; set; }
public string Surname { get; set; }
public int Age { get; set; }
WebApiClient.cs
internal class WebApiClient : IDisposable
{
private bool _isDispose;
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
public void Dispose(bool disposing)
{
if (!_isDispose)
{
if (disposing)
{
}
}
_isDispose = true;
}
private void SetHeaderParameters(WebClient client)
{
client.Headers.Clear();
client.Headers.Add("Content-Type", "application/json");
client.Encoding = Encoding.UTF8;
}
public async Task<T> PostJsonWithModelAsync<T>(string address, string data,)
{
using (var client = new WebClient())
{
SetHeaderParameters(client);
string result = await client.UploadStringTaskAsync(address, data); // method:
//The HTTP method used to send the file to the resource. If null, the default is POST
return JsonConvert.DeserializeObject<T>(result);
}
}
}
业务调用方法
public async Task<ResultDTO> GetResultAsync(PostModel model)
{
try
{
using (var client = new WebApiClient())
{
var serializeModel= JsonConvert.SerializeObject(model);// using Newtonsoft.Json;
var response = await client.PostJsonWithModelAsync<ResultDTO>("http://www.website.com/api/create", serializeModel);
return response;
}
}
catch (Exception ex)
{
throw new Exception(ex.Message);
}
}
【讨论】:
大多数答案都是旧的。只是想分享对我有用的东西。为了异步做事,即在 .NET 6.0 Preview 7 中使用 WebClient 异步将数据发布到特定 URL,.NET Core 和其他版本可以使用 WebClient.UploadStringTaskAsync Method 完成。
使用命名空间System.Net; 和一个类ResponseType 来捕获来自服务器的响应,我们可以使用该方法将POST 数据发送到特定的URL。请确保在调用此方法时使用await 关键字
public async Task<ResponseType> MyAsyncServiceCall()
{
try
{
var uri = new Uri("http://your_uri");
var body= "param1=value1¶m2=value2¶m3=value3";
using (var wc = new WebClient())
{
wc.Headers[HttpRequestHeader.Authorization] = "yourKey"; // Can be Bearer token, API Key etc.....
wc.Headers[HttpRequestHeader.ContentType] = "application/json"; // Is about the payload/content of the current request or response. Do not use it if the request doesn't have a payload/ body.
wc.Headers[HttpRequestHeader.Accept] = "application/json"; // Tells the server the kind of response the client will accept.
wc.Headers[HttpRequestHeader.UserAgent] = "PostmanRuntime/7.28.3";
string result = await wc.UploadStringTaskAsync(uri, body);
return JsonConvert.DeserializeObject<ResponseType>(result);
}
}
catch (Exception e)
{
throw new Exception(e.Message);
}
}
【讨论】:
这里是明确的答案:
public String sendSMS(String phone, String token) {
WebClient webClient = WebClient.create(smsServiceUrl);
SMSRequest smsRequest = new SMSRequest();
smsRequest.setMessage(token);
smsRequest.setPhoneNo(phone);
smsRequest.setTokenId(smsServiceTokenId);
Mono<String> response = webClient.post()
.uri(smsServiceEndpoint)
.header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
.body(Mono.just(smsRequest), SMSRequest.class)
.retrieve().bodyToMono(String.class);
String deliveryResponse = response.block();
if (deliveryResponse.equalsIgnoreCase("success")) {
return deliveryResponse;
}
return null;
}
【讨论】: