web-dev-qa-db-fra.com

Comment écrire une requête HTTP

Bonjour, j'essaye d'écrire une requête HTTP en C # (Post), mais j'ai besoin d'aide avec une erreur

Expl: Je veux envoyer le contenu d'un fichier DLC au serveur et recevoir le contenu décrypté.

Code C #

public static void decryptContainer(string dlc_content) 
{
    HttpWebRequest request = (HttpWebRequest)WebRequest.Create("http://dcrypt.it/decrypt/paste");
    request.Method = "POST";
    request.ContentType = "application/x-www-form-urlencoded";
    request.Accept = "Accept=text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8";

    using (StreamWriter writer = new StreamWriter(request.GetRequestStream(), Encoding.ASCII))
    {
        writer.Write("content=" + dlc_content);
    }

    HttpWebResponse response = (HttpWebResponse)request.GetResponse();

    using (StreamReader reader = new StreamReader(response.GetResponseStream()))
    {
        Console.WriteLine(reader.ReadToEnd());
    }
}

et ici j'ai la demande html

<form action="/decrypt/paste" method="post">
    <fieldset>
        <p class="formrow">
          <label for="content">DLC content</label>
          <input id="content" name="content" type="text" value="" />
         </p>
        <p class="buttonrow"><button type="submit">Submit »</button></p>
    </fieldset>
</form>

Message d'erreur:

{
    "form_errors": {
      "__all__": [
        "Sorry, an error occurred while processing the container."
       ]
    }
}

Ce serait très utile si quelqu'un pouvait m'aider à résoudre le problème!

13
Googles

Vous n'avez pas défini de longueur de contenu, ce qui pourrait causer des problèmes. Vous pouvez aussi essayer d’écrire des octets directement dans le flux au lieu de le convertir en ASCII first ..

public static void decryptContainer(string dlc_content) 
   {
        HttpWebRequest request = (HttpWebRequest)WebRequest.Create("http://dcrypt.it/decrypt/paste");
        request.Method = "POST";
        request.ContentType = "application/x-www-form-urlencoded";
        request.Accept = "Accept=text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8";

        byte[] _byteVersion = Encoding.ASCII.GetBytes(string.Concat("content=", dlc_content));

        request.ContentLength = _byteVersion.Length

        Stream stream = request.GetRequestStream();
        stream.Write(_byteVersion, 0, _byteVersion.Length);
        stream.Close();

        HttpWebResponse response = (HttpWebResponse)request.GetResponse();

        using (StreamReader reader = new StreamReader(response.GetResponseStream()))
        {
            Console.WriteLine(reader.ReadToEnd());
        }
    }

J'ai personnellement trouvé que poster comme ça était un peu "fidélité" dans le passé. Vous pouvez également essayer de définir ProtocolVersion sur la demande.

13
chemicalNova

Je simplifierais votre code, comme ceci:

public static void decryptContainer(string dlc_content) 
{
    using (var client = new WebClient())
    {
        var values = new NameValueCollection
        {
            { "content", dlc_content }
        };
        client.Headers[HttpRequestHeader.Accept] = "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8";
        string url = "http://dcrypt.it/decrypt/paste";
        byte[] result = client.UploadValues(url, values);
        Console.WriteLine(Encoding.UTF8.GetString(result));
    }
}

Cela garantit également que les paramètres de la demande sont correctement codés.

6
Darin Dimitrov
public string void decryptContainer(string dlc_content) //why not return a string, let caller decide what to do with it.
{
    HttpWebRequest request = (HttpWebRequest)WebRequest.Create("http://dcrypt.it/decrypt/paste");
    request.Method = "POST";
    request.ContentType = "application/x-www-form-urlencoded";
    request.Accept = "Accept=text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8";//sure this is needed? Maybe just match the one content-type you expect.
    using (StreamWriter writer = new StreamWriter(request.GetRequestStream(), Encoding.ASCII))
    {
        writer.Write("content=" + Uri.EscapeDataString(dlc_content));//escape the value of dlc_content so that the entity sent is valid application/x-www-form-urlencoded
    }
    using(HttpWebResponse response = (HttpWebResponse)request.GetResponse())//this should be disposed when finished with.
    using (StreamReader reader = new StreamReader(response.GetResponseStream()))
    {
        return reader.ReadToEnd();
    }
}

Il pourrait toujours y avoir un problème avec ce qui est réellement envoyé.

2
Jon Hanna

request.ContentLength doit également être défini.

Aussi, y a-t-il une raison pour laquelle vous codez ASCII par rapport à UTF8?

1
digitalmarks

Un problème que je vois tout de suite est qu’il est nécessaire de coder l’URL du paramètre content. Utilisez HttpUtility.UrlEncode() pour cela . En dehors de cela, il pourrait y avoir d'autres problèmes, mais il est difficile de dire que vous ne savez pas quel service est fourni. L'erreur est trop générique et pourrait signifier n'importe quoi

1
Ilia G

Comme je ne peux pas commenter la solution de Jon Hanna. Cela a résolu le problème pour moi: Uri.EscapeDataString

        // this is what we are sending
        string post_data = "content=" + Uri.EscapeDataString(dlc_content);

        // this is where we will send it
        string uri = "http://dcrypt.it/decrypt/paste";

        // create a request
        HttpWebRequest request = (HttpWebRequest)WebRequest.Create(uri);
        request.KeepAlive = false;
        request.ProtocolVersion = HttpVersion.Version10;
        request.Method = "POST";

        // turn our request string into a byte stream
        byte[] postBytes = Encoding.ASCII.GetBytes(post_data);

        // this is important - make sure you specify type this way
        request.ContentType = "application/x-www-form-urlencoded";
        request.ContentLength = postBytes.Length;

        Stream requestStream = request.GetRequestStream();

        // now send it
        requestStream.Write(postBytes, 0, postBytes.Length);
        requestStream.Close();

        // grab te response and print it out to the console along with the status code
        HttpWebResponse response = (HttpWebResponse)request.GetResponse();
        Console.WriteLine(new StreamReader(response.GetResponseStream()).ReadToEnd());
        Console.WriteLine(response.StatusCode);
0
Luca Salzani

Obtenez d'abord le flux associé à la réponse, puis transmettez-le au Streamreader comme ci-dessous:

    Stream receiveStream = response.GetResponseStream();       

    using (StreamReader reader = new StreamReader(receiveStream, Encoding.ASCII))
    {
        Console.WriteLine(reader.ReadToEnd());
    }
0
Standage