2010-10-15 32 views
1

J'envoie une requête HTTP PUT à partir d'une application WinForms et je souhaite envoyer un léger filet de données PUT à la page qui va écrire des messages dans une base de données lorsque les données PUT arrivent. J'utilise WebRequest et j'ai défini SendChunked sur true, mais il semble seulement envoyer un fragment après que 8 Ko de données aient été écrites dans le flux de requêtes.Puis-je dire à WebRequest quand envoyer un fragment à partir du flux de requêtes?

Pire encore, la page Web semble cesser de recevoir après environ 42 Ko et l'expéditeur émet une exception WebException après environ 77 Ko avec le message "La requête a été abandonnée: la demande a été annulée". En fait, j'envoie de très petites quantités de données dans chaque message, donc si je pouvais convaincre WebRequest d'envoyer juste un petit morceau contenant chaque message, ça irait.

Voici ce que j'expérimente avec à ce jour:

 var request = 
      (HttpWebRequest)WebRequest.Create("http://localhost/test.php"); 

     request.Method = "PUT"; 
     request.Timeout = 300 * 1000; 
     request.SendChunked = true; 
     request.AllowWriteStreamBuffering = false; 
     request.ContentType = "application/octet-stream"; 
     using (var post = new StreamWriter(request.GetRequestStream())) 
     { 
      post.AutoFlush = true; 
      for (int i = 0; i < 100; i++) 
      { 
       if (i > 0) 
       { 
        // force flushing previous chunk 
        post.Write(new String(' ', 1048)); 
        Thread.Sleep(2 * 1000); 
       } 
       Console.Out.WriteLine("Requesting {0} at {1}.", i, DateTime.Now); 
       string chunk = i.ToString(); 
       post.WriteLine(i); 
      } 
     } 

J'écris 1KB d'espaces après chaque message pour essayer de forcer le WebRequest à envoyer un morceau plus tôt.

Répondre

1

Si je comprends bien votre question, vous souhaitez émettre une seule demande PUT. Dans le cadre de la demande, vous souhaitez envoyer des données tronquées et vous souhaitez que le serveur agisse sur chaque tronçon qu'il voit.

Je ne pense pas que cela sera possible très facilement en utilisant HttpWebRequest. Comme vous l'avez remarqué, alors que HWR enverra des données segmentées, il ne vous donne pas le contrôle sur l'endroit où commence et se termine exactement un morceau. Ensuite, même si vous pouviez retirer le côté client, en écrivant une implémentation Socket personnalisée comme le suggère Don, vous ne pouvez toujours pas garantir que le serveur Web donnera le contrôle à votre application pour chaque segment qu'il reçoit. Le serveur Web peut décider de mettre en mémoire tampon plusieurs blocs et de les donner tous à l'application en même temps. Je suggérerais que vous repensez votre conception, et ayez un modèle simple basé sur la demande/réponse où la demande + données constitue une action que le serveur doit prendre.

1

Si personne n'a des suggestions plus élégantes, je suppose que je pourrais ouvrir un socket brut et implémenter le codage en morceaux moi-même. Il y a une description raisonnable dans this answer.