Intestazione personalizzata alla richiesta HttpClient


140

Come faccio ad aggiungere un'intestazione personalizzata a una HttpClientrichiesta? Sto usando il PostAsJsonAsyncmetodo per pubblicare il JSON. L'intestazione personalizzata che dovrei aggiungere è

"X-Version: 1"

Questo è quello che ho fatto finora:

using (var client = new HttpClient()) {
    client.BaseAddress = new Uri("https://api.clickatell.com/");
    client.DefaultRequestHeaders.Accept.Clear();
    client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", "xxxxxxxxxxxxxxxxxxxx");
    client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
    var response = client.PostAsJsonAsync("rest/message", svm).Result;
}


@Liam: la mia domanda era come aggiungere intestazioni personalizzate. Dove come l'altra domanda era come aggiungere le intestazioni
Libin Joseph

2
Penso che sia stato riscontrato che non dovremmo smaltire HttpClient. aspnetmonsters.com/2016/08/2016 08-27-27
Don Rolling

Risposte:


57
var request = new HttpRequestMessage {
    RequestUri = new Uri("[your request url string]"),
    Method = HttpMethod.Post,
    Headers = {
        { "X-Version", "1" } // HERE IS HOW TO ADD HEADERS,
        { HttpRequestHeader.Authorization.ToString(), "[your authorization token]" },
        { HttpRequestHeader.ContentType.ToString(), "multipart/mixed" },//use this content type if you want to send more than one content type
    },
    Content = new MultipartContent { // Just example of request sending multipart request
        new ObjectContent<[YOUR JSON OBJECT TYPE]>(
            new [YOUR JSON OBJECT TYPE INSTANCE](...){...}, 
            new JsonMediaTypeFormatter(), 
            "application/json"), // this will add 'Content-Type' header for the first part of request
        new ByteArrayContent([BINARY DATA]) {
            Headers = { // this will add headers for the second part of request
                { "Content-Type", "application/Executable" },
                { "Content-Disposition", "form-data; filename=\"test.pdf\"" },
            },
        },
    },
};

38
la risposta è estremamente confusa ... perché stai introducendo codice per documenti, blank.pdf, ecc? istanziare le classi bytearray per passare le intestazioni personalizzate all'interno del parametro Content?
heug

2
@heug Bene. Se stai cercando un header puoi vederlo. Il contenuto è presente qui al fine di completare l'immagine perché molto probabilmente si desidera aggiungere alcuni contenuti alla richiesta. E per non essere noioso il contenuto è complicato e contiene sia dati JSON che binari.
Anubis,

2
sembra solo più semplice farlo in questo modo: crea StringContent usando il tuo contenuto JSON, crea un messaggio HTTP con il tuo metodo e URI, quindi aggiungi intestazioni come message.Headers.Add ("x": "y") .... quindi passali in una risposta var come "var response = waitit httpClient.SendAsync (message);"
Eug

@heug Lo ricorderò per il furute. Grazie!
Anubis,

3
Quale riga della risposta accettata sopra implementa effettivamente l'intestazione richiesta dall'OP, versione X? Perché questa è considerata la risposta accettata?
Ron,

215

Ho trovato la risposta alla mia domanda.

client.DefaultRequestHeaders.Add("X-Version","1");

Ciò dovrebbe aggiungere un'intestazione personalizzata alla tua richiesta


50
No non lo fa. Questa risposta deve essere visualizzata con cautela, poiché le intestazioni delle richieste predefinite vengono inviate con ogni richiesta. Dovresti compilare la tua richiesta come suggerito da @Anubi. DefaultsRequestHeaders deve essere popolato quando si crea HttpClient.
Ruhrpottpatriot,

6
Funziona solo perché stai istanziando un nuovo HttpClient per ogni richiesta. Non è così che dovrebbe essere usata questa classe: dovrebbe essere un campo statico, riutilizzato per tutte le richieste, almeno quelle per lo stesso endpoint. Vedi la documentazione e gli innumerevoli post sul blog là fuori. Quindi, come ovvio, come sottolinea @Ruhrpottpatriot, la modifica delle intestazioni predefinite influirà su tutte le richieste.
kamilk,

@Ruhrpottpatriot Cosa c'è di sbagliato nell'invio dell'intestazione per ogni richiesta?
David Klempfner,

1
@ajbeaven No, non è quello che dice. L'esempio nella parte superiore della pagina mostra il metodo principale dell'app, quindi anche se HttpClient è eliminato, la stessa istanza viene utilizzata per tutta la durata dell'applicazione e questo è corretto per quanto riguarda ciò che la documentazione dice un po ' un po 'più in basso: "HttpClient deve essere istanziato una volta e riutilizzato per tutta la vita di un'applicazione" . Di seguito questo paragrafo è un esempio che consiglia di assegnare un HttpClient a un campo statico.
kamilk,

1
@Kamilk, hai ragione, quell'esempio mi ha sbagliato. Grazie per avermi messo bene :)
ajbeaven

79

Ecco una risposta basata su quella di Anubi (che è un approccio migliore in quanto non modifica le intestazioni per ogni richiesta) ma che è più equivalente al codice nella domanda originale:

using Newtonsoft.Json;
...

    var client = new HttpClient();
    var httpRequestMessage = new HttpRequestMessage
        {
            Method = HttpMethod.Post,
            RequestUri = new Uri("https://api.clickatell.com/rest/message"),
            Headers = { 
                { HttpRequestHeader.Authorization.ToString(), "Bearer xxxxxxxxxxxxxxxxxxxx" },
                { HttpRequestHeader.Accept.ToString(), "application/json" },
                { "X-Version", "1" }
            },
            Content = new StringContent(JsonConvert.SerializeObject(svm))
        };

    var response = client.SendAsync(httpRequestMessage).Result;

@RossPresser sicuramente no. Content-Type è un'intestazione di contenuto.
Panagiotis Kanavos,

1
D'accordo, questa è la risposta. Viene illustrato come aggiungere l'intestazione richiesta da OP. Ha risposto anche alla mia domanda.
Ron,

1
Cordiali saluti, penso che HttpRequestHeader.Accessdovrebbe essere HttpRequestHeader.Accept.
Mass Dot Net,

che cosa è svm a proposito?
Aswzen

@aswzen Viene dalla domanda del PO: qualcosa di modello che immagino. L'oggetto viene serializzato.
Chris Peacock,

2

C'è una Headersproprietà nella HttpRequestMessageclasse. È possibile aggiungere intestazioni personalizzate lì, che verranno inviate con ogni richiesta HTTP. Il DefaultRequestHeadersnella HttpClientclasse, d'altra parte, imposta le intestazioni da inviare con ogni richiesta inviata utilizzando quell'oggetto client, da cui il nome Intestazioni richieste predefinite .

Spero che questo renda le cose più chiare, almeno per qualcuno che vedrà questa risposta in futuro.


1
No, non lo rende più chiaro. In entrambi i casi stai dicendo che stai inviando le intestazioni per ogni richiesta. Qual è la differenza?
Joedotnot non è il

3
Headersè una proprietà di un singolo HttpRequestMessageoggetto. In questo modo è possibile creare messaggi diversi con intestazioni diverse. DefaultRequestHeadersè una proprietà HttpClientdell'oggetto; se vengono inviati più messaggi attraverso un determinato HttpClient, a tutti questi messaggi verrà DefaultRequestHeadersaggiunto lo stesso alle singole intestazioni del messaggio.
Ross Presser,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.