C# - HttpWebRequest POST
Je suis en train de faire un POST de Http à un serveur web Apache.
Je trouve que la mise ContentLength semble être nécessaire pour que la demande de travail.
Je préfère créer un XmlWriter directement à partir de GetRequestStream() et set SendChunked de vrai, mais la demande se bloque indéfiniment.
Ici est de savoir comment ma demande est créée:
private HttpWebRequest MakeRequest(string url, string method)
{
HttpWebRequest request = HttpWebRequest.Create(url) as HttpWebRequest;
request.Method = method;
request.Timeout = Timeout; //Property in my class, assume it's 10000
request.ContentType = "text/xml"; //I am only writing xml with XmlWriter
if (method != WebRequestMethods.Http.Get)
{
request.SendChunked = true;
}
return request;
}
Comment puis-je faire SendChunked travail donc je n'ai pas de définir ContentLength? Je ne vois pas une raison pour stocker les XmlWriter de la chaîne, quelque part avant de les envoyer au serveur.
EDIT: Voici mon code à l'origine du problème:
using (Stream stream = webRequest.GetRequestStream())
{
using (XmlWriter writer = XmlWriter.Create(stream, XmlTags.Settings))
{
Generator.WriteXml<TRequest>(request, writer);
}
}
Avant que je n'ai pas de l'aide sur le Flux de l'objet renvoyé de GetRequestStream(), j'ai supposé XmlWriter fermé le flux lors de son élimination, mais ce n'est pas le cas.
L'une des réponses ci-dessous, laissez-moi à présent. Je vais les marquer comme réponse.
Autant que HttpWebRequest est concerné, mon code d'origine fonctionne très bien.
Je n'ai pas de windows serveur pour l'essayer, et j'avais dû avoir à passer du temps à écrire du code C# pour lire le message. J'ai envie de régler un paramètre sur HttpWebRequest devrait résoudre ce problème.
OriginalL'auteur jonathanpeppers | 2009-12-14
Vous devez vous connecter pour publier un commentaire.
Cela devrait fonctionner de la même manière que vous l'avez écrit. Peut-on voir le code qui en fait ne le téléchargement? Êtes-vous se souvenir de fermer le flux de données?
WriteEndDocument
n'a pas fait fermer le flux de données. Quelque part dans votre code, vous êtes en invoquantGetRequestStream
(ouBeginGetRequestStream
); une fois que vous avez fini d'écrire votre XML, vous devez invoquer leClose
méthode sur cetteStream
instance. Si vous ne le faites pas, il ne sais pas quand vous avez terminé le téléchargement et la connexion va s'asseoir à jamais ouvert.Vous êtes
using
laXmlWriter
, qui va disposer l'XmlWriter
et seul leXmlWriter
. C'est le Stream vous devez appelerDispose
(ouClose
, qui est la méthode recommandée).XmlWriter
va pas le faire pour vous.OriginalL'auteur Aaronaught
Regardant l'exemple à http://msdn.microsoft.com/en-us/library/system.net.httpwebrequest.sendchunked.aspx ils ont toujours une longueur de contenu. Vraiment la ligne de fond est que si vous envoyez des données, vous devez indiquer au récepteur de la quantité de données que vous allez envoyer. Pourquoi ne savez-vous pas quelle quantité de données que vous envoyez, avant de vous envoyer la demande?
ContentLength:
La Valeur De La Propriété
Type: System..::.Int64
Le nombre d'octets de données à envoyer à la ressource Internet. La valeur par défaut est -1, ce qui indique que la propriété n'a pas été fixé et qu'il n'y a pas de demande de données à envoyer.
Modifier pour Aaron (je me suis trompé):
À Partir Du Système.Net.HttpWebRequest.SerializeHeaders():
ContentLength
propriété lorsque vous utilisezSendChunked = true
. Un paramètre remplace l'autre.w3.org/Protocols/rfc2616/rfc2616-sec4.html#sec4.4 "Si un message est reçu avec un Encodage de Transfert de champ d'en-tête et le Contenu de la Longueur de champ d'en-tête, celui-ci DOIT être ignorée." Il est donc autorisé conformément à la RFC, mais cela ne signifie pas qu'il est pris en charge par l'application de la réception de la POSTE. Le plus simple est d'obtenir la longueur et la définir, mais quel plaisir que ce serait 🙂 C'est toujours un plaisir d'explorer des solutions optimisées.
Ainsi, l'application de la réception de la POSTE est d'Apache, comme indiqué dans la question d'origine. Sauf si c'est une très, très vieille version de Apache, il soutiendra des fragments de codage.
J'ai peut-être raté quelque chose mais je ne vois pas en lui un paramètre d'Encodage de Transfert de valeur dans son exemple. Aussi, nous ne sommes pas vraiment discuter de la spécification HTTP, mais plutôt HttpRequest .NET objet et la façon dont il fonctionne. Il est très possible l'objet HttpRequest nécessite des paramètres qui violerait une spec pour fonction propertly puis de l'artisanat d'une demande qui est à spec. Je vais regarder le HttpRequest de classe et voir ce que je trouve.
Mon édité le post est un exemple pour montrer que ce n'est pas le cas, du moins pas dans le
TransferEncoding
de la propriété. RéglageSendChunked
=true
a toujours un videTransferEncoding
valeur. Si cela est vrai lorsque la demande est envoyée, je ne peux pas dire.OriginalL'auteur Cory Charlton