Pourquoi l’envoi de données de publication avec WebRequest prend-il tant de temps?

Je crée actuellement une application C # à intégrer à un système en ligne php / MySQL. L’application doit envoyer des données de publication aux scripts et obtenir la réponse.

Quand j’envoie les données suivantes

 nom d'utilisateur = test & mot de passe = test  

Je reçois les réponses suivantes …

 Demande de départ à 22/04/2010 12:15:42 La création d'une demande est terminée: a pris 00: 00: 00.0570057 Transmission des données à 22/04/2010 12:15:42 Transmis les données: a pris 00: 00: 06.9316931 << - Obtention de la réponse le 22/04/2010 12 h 15:49 Obtention de la réponse 00: 00: 00.0360036 Réponse terminée 00: 00: 00.0360036 L'appel complet a pris 00: 00: 07.0247024 

Comme vous pouvez le constater, il faut 6 secondes pour envoyer les données au script, j’ai fait d’autres tests en envoyant des données à partir de telnet et en envoyant des données de publication d’un fichier local à l’URL et elles ne prennent même pas une seconde, c’est donc pas un problème avec le script hébergé sur le site.

Pourquoi faut-il 6 secondes pour transmettre les données quand il s’agit de deux chaînes simples?

J’utilise une classe personnalisée pour envoyer les données

class httppostdata { WebRequest request; WebResponse response; public ssortingng senddata(ssortingng url, ssortingng postdata) { var start = DateTime.Now; Console.WriteLine("Starting request at " + start.ToSsortingng()); // create the request to the url passed in the paramaters request = (WebRequest)WebRequest.Create(url); // set the method to post request.Method = "POST"; // set the content type and the content length request.ContentType = "application/x-www-form-urlencoded"; request.ContentLength = postdata.Length; // convert the post data into a byte array byte[] byteData = Encoding.UTF8.GetBytes(postdata); var end1 = DateTime.Now; Console.WriteLine("Finished creating request : took " + (end1 - start)); var start2 = DateTime.Now; Console.WriteLine("Transmitting data at " + start2.ToSsortingng()); // get the request stream and write the data to it Stream dataStream = request.GetRequestStream(); dataStream.Write(byteData, 0, byteData.Length); dataStream.Close(); var end2 = DateTime.Now; Console.WriteLine("Transmitted the data : took " + (end2 - start2)); // get the response var start3 = DateTime.Now; Console.WriteLine("Getting the response at " + start3.ToSsortingng()); response = request.GetResponse(); //Console.WriteLine(((WebResponse)response).StatusDescription); dataStream = response.GetResponseStream(); StreamReader reader = new StreamReader(dataStream); var end3 = DateTime.Now; Console.WriteLine("Getting response " + (end3 - start3)); // read the response ssortingng serverresponse = reader.ReadToEnd(); var end3a = DateTime.Now; Console.WriteLine("Finished response " + (end3a - start3)); Console.WriteLine("Entire call took " + (end3a - start)); //Console.WriteLine(serverresponse); reader.Close(); dataStream.Close(); response.Close(); return serverresponse; } } 

Et pour l’appeler j’utilise

 private void btnLogin_Click(object sender, EventArgs e) { // ssortingng postdata; if (txtUsername.Text.Length < 3 || txtPassword.Text.Length < 3) { MessageBox.Show("Missing your username or password."); } else { string postdata = "username=" + txtUsername.Text + "&password=" + txtPassword.Text; httppostdata myPost = new httppostdata(); string response = myPost.senddata("http://www.domainname.com/scriptname.php", postdata); MessageBox.Show(response); } } 

Assurez-vous de définir explicitement la propriété proxy de WebRequest sur null, sinon le système essaiera de détecter automatiquement les parameters de proxy, ce qui peut prendre un certain temps.

Les chances sont que parce que, dans votre test, vous appelez ceci une seule fois, le délai que vous voyez est le code C # compilé par JIT.

Un meilleur test serait d’appeler ceci deux fois, et de jeter les timings de la première fois et de voir s’ils sont meilleurs.

Un test encore plus efficace consisterait à ignorer la première série de minutages, puis à l’exécuter plusieurs fois et à prendre une moyenne, bien que pour une vue “indicative” très floue, ce n’est probablement pas nécessaire.

Soit dit en passant, pour ce type de synchronisation, il est préférable d’utiliser la classe System.DateTime sur System.DateTime .

[EDIT] En outre, notant la suggestion de Mant101 concernant les procurations, si le paramètre no proxy ne résout pas le problème, vous pouvez configurer Fiddler et configurer votre demande pour qu’elle utilise Fiddler en tant que proxy. Cela vous permettrait d’intercepter les appels http réels afin d’obtenir une meilleure ventilation des timings des appels http eux-mêmes en dehors du cadre.