6
votes

Appelez HTTP GET avec les paramètres de contenu du corps JSON

Comment puis-je appeler HTTP GET en utilisant les paramètres JSON dans le corps du contenu?

J'ai essayé ceci:

HttpWebRequest.WebRequest.Create(_uri);
httpWebRequest.ContentType = "application/json";
httpWebRequest.Method = "GET";
httpWebRequest.Headers.Add("X-AUTH-TOKEN", _apiKey);

using(var streamWriter = new StreamWriter(httpWebRequest.GetRequestStream())) {
  string _json = "\"{\"filter\": {\"relation\": \"equals\", \"attribute\": \"state\", \"value\": \"CA\"  },  \"insights\": {\"field\": \"family.behaviors\",  \"calculations\": [\"fill_count\"]}}";

  streamWriter.Write(_json);
  streamWriter.Flush();
  streamWriter.Close();
}

var httpResponse = (HttpWebResponse) httpWebRequest.GetResponse();
using(var streamReader = new StreamReader(httpResponse.GetResponseStream())) {
  var result = streamReader.ReadToEnd();
}

mais cela lève une exception:

"Impossible d'envoyer un corps de contenu avec ce type de verbe."

c#

4 commentaires

Utilisez POST si vous souhaitez enregistrer et utilisez PUT si vous souhaitez mettre à jour dans httpWebRequest.


Vous pouvez le cocher en définissant la méthode sur POST, puis en écrivant le corps, puis en remettant la méthode en GET. Cela fonctionne, mais je ne sais pas si cela envoie réellement le corps après une chose aussi sale. Vous aurez peut-être besoin d'une capture de paquets / d'un accès aux résultats du serveur / test pour comprendre cela.


Utilisez POST comme type de méthode. Et si vous utilisez HttpClient, ce serait mieux. Comme vous obtiendrez la méthode async hors de la boîte et elle est facile à utiliser.


Copie possible de Possible pour HttpClient d'envoyer du contenu ou corps pour la demande GET?


4 Réponses :


0
votes

GET ne le recevra que.

Si vous avez besoin de spécifier des paramètres, veuillez les inclure dans l'URL.
Ou vous pouvez envoyer JSON BODY si POST ou PUT.

Méthodes de requête HTTP

HTTP définit un ensemble de méthodes de requête pour indiquer l'action souhaitée à effectuer pour une ressource donnée. Bien qu'elles puissent également être des noms, ces méthodes de requête sont parfois appelées verbes HTTP. Chacun d'eux implémente une sémantique différente, mais certaines caractéristiques communes sont partagées par un groupe d'entre eux: par ex. une méthode de requête peut être sûre, idempotente ou mise en cache.

  • OBTENIR
    La méthode GET demande une représentation de la ressource spécifiée. Les requêtes utilisant GET ne doivent récupérer que des données.
  • HEAD
    La méthode HEAD demande une réponse identique à celle d'une requête GET, mais sans le corps de la réponse.
  • POST
    La méthode POST est utilisée pour soumettre une entité à la ressource spécifiée, provoquant souvent un changement d'état ou des effets secondaires sur le serveur.
  • PUT
    La méthode PUT remplace toutes les représentations actuelles de la ressource cible par la charge utile de la requête.

En plus:

J'ai trouvé ça. Une longue discussion a eu lieu.
HTTP GET avec le corps de la requête

Cela signifie qu'il est possible d'envoyer BODY avec GET, mais l'envoi d'un corps de charge utile sur une requête GET peut amener certaines implémentations existantes à rejeter la requête (comme Proxy au milieu de la route).

Veuillez lire attentivement cet article car il y a de nombreux autres points auxquels prêter attention.


Au fait, il semble que vous puissiez envoyer GET avec body en utilisant l'option -i de la commande cURL.

Requête Curl GET avec paramètre json


0 commentaires

0
votes

Même s'il est techniquement autorisé d'envoyer un corps avec Get demandes, Microsoft a décidé pour vous que vous ne pouvez pas faire cela.

Cela peut être vu dans HttpWebRequest code source :

if (onRequestStream) {
// prevent someone from getting a request stream, if the protocol verb/method doesn't support it
    throw new ProtocolViolationException(SR.GetString(SR.net_nouploadonget));
}

Vous devez donc changez votre verbe en Put ou Post ou ayez un autre solution de contournement .


0 commentaires

1
votes

C'est tout à fait possible, mais vous devez utiliser la nouvelle classe HttpClient : https: // stackoverflow .com / a / 47902348/70345


0 commentaires

4
votes

Si vous utilisez .NET Core, le nouveau HttpClient peut gérer cela. Sinon, vous pouvez utiliser le package System.Net.Http.WinHttpHandler , mais il a une tonne de dépendances. Consultez la réponse

https://stackoverflow.com/a/47902348/1030010

pour comment utiliser ces deux éléments.

Je ne peux pas utiliser .NET core et je ne veux pas installer System.Net.Http.WinHttpHandler . Je l'ai résolu en utilisant la réflexion, pour tromper WebRequest qu'il est légal d'envoyer un corps avec une requête GET (qui est selon la dernière RFC). Ce que je fais est de définir ContentBodyNotAllowed sur false pour le verbe HTTP "GET".

var request = WebRequest.Create(requestUri);

request.ContentType = "application/json";
request.Method = "GET";

var type = request.GetType();
var currentMethod = type.GetProperty("CurrentMethod", BindingFlags.NonPublic | BindingFlags.Instance).GetValue(request);

var methodType = currentMethod.GetType();
methodType.GetField("ContentBodyNotAllowed", BindingFlags.NonPublic | BindingFlags.Instance).SetValue(currentMethod, false);

using (var streamWriter = new StreamWriter(request.GetRequestStream()))
{
    streamWriter.Write("<Json string here>");
}

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

Notez cependant que l'attribut ContentBodyNotAllowed appartient à un champ statique, donc lorsque sa valeur change, il reste en vigueur pour le reste du programme. Ce n'est pas un problème pour mes besoins.


1 commentaires

En tant que personne qui comprend l'intégration des systèmes et les difficultés avec les proxys et les serveurs tiers signalant ce type de transaction comme une demande mal formée ... je tiens à vous remercier pour cette découverte. Si mes propres MicroServices se parlent et que je veux mettre un corps dans un GET ... je devrais être autorisé. J'ai testé cela et cela fonctionne parfaitement.