c# - net - ¿Cómo se establece una cadena grande dentro de HttpContent cuando se utiliza HttpClient?
model to httpcontent c# (3)
Entonces, creé un HttpClient
y estoy publicando datos usando HttpClient.PostAsync()
.
Configuré el HttpContent
usando
HttpContent content = new FormUrlEncodedContent(post_parameters)
; donde post_parameters
es una lista de pares de valores clave List<KeyValuePair<string, string>>
El problema es que cuando HttpContent
tiene un gran valor (una imagen convertida a base64 para ser transmitida) obtengo una URL que es un error demasiado largo. Eso tiene sentido, porque la URL no puede superar los 32,000 caracteres. Pero, ¿cómo puedo agregar los datos en HttpContent
si no es así?
Por favor ayuda.
Este código funciona para mí, básicamente usted envía los datos de la publicación "application / x-www-form-urlencoded" dentro del contenido de la cadena sobre el cliente http, espero que esto pueda ayudar a cualquiera que tenga el mismo problema que yo.
void sendDocument()
{
string url = "www.mysite.com/page.php";
StringBuilder postData = new StringBuilder();
postData.Append(String.Format("{0}={1}&", HttpUtility.HtmlEncode("prop"), HttpUtility.HtmlEncode("value")));
postData.Append(String.Format("{0}={1}", HttpUtility.HtmlEncode("prop2"), HttpUtility.HtmlEncode("value2")));
StringContent myStringContent = new StringContent(postData.ToString(), Encoding.UTF8, "application/x-www-form-urlencoded");
HttpClient client = new HttpClient();
HttpResponseMessage message = client.PostAsync(url, myStringContent).GetAwaiter().GetResult();
string responseContent = message.Content.ReadAsStringAsync().GetAwaiter().GetResult();
}
Lo descubrí con la ayuda de mi amigo. Lo que desearía hacer es evitar usar FormUrlEncodedContent (), ya que tiene restricciones en el tamaño de la uri. En cambio, puedes hacer lo siguiente:
var jsonString = JsonConvert.SerializeObject(post_parameters);
var content = new StringContent(jsonString, Encoding.UTF8, "application/json");
Aquí, no necesitamos usar HttpContent para publicar en el servidor, ¡StringContent hace el trabajo!
FormUrlEncodedContent
internamente usa Uri.EscapeDataString
: de la reflexión, puedo ver que este método tiene constantes que limitan el tamaño de la longitud de la solicitud.
Una posible solución es crear una nueva implementación de FormUrlEncodedContent
utilizando System.Net.WebUtility.UrlEncode
(.net 4.5) para eludir esta limitación.
public class MyFormUrlEncodedContent : ByteArrayContent
{
public MyFormUrlEncodedContent(IEnumerable<KeyValuePair<string, string>> nameValueCollection)
: base(MyFormUrlEncodedContent.GetContentByteArray(nameValueCollection))
{
base.Headers.ContentType = new MediaTypeHeaderValue("application/x-www-form-urlencoded");
}
private static byte[] GetContentByteArray(IEnumerable<KeyValuePair<string, string>> nameValueCollection)
{
if (nameValueCollection == null)
{
throw new ArgumentNullException("nameValueCollection");
}
StringBuilder stringBuilder = new StringBuilder();
foreach (KeyValuePair<string, string> current in nameValueCollection)
{
if (stringBuilder.Length > 0)
{
stringBuilder.Append(''&'');
}
stringBuilder.Append(MyFormUrlEncodedContent.Encode(current.Key));
stringBuilder.Append(''='');
stringBuilder.Append(MyFormUrlEncodedContent.Encode(current.Value));
}
return Encoding.Default.GetBytes(stringBuilder.ToString());
}
private static string Encode(string data)
{
if (string.IsNullOrEmpty(data))
{
return string.Empty;
}
return System.Net.WebUtility.UrlEncode(data).Replace("%20", "+");
}
}
Para enviar contenido de gran tamaño, es mejor usar StreamContent .