web-dev-qa-db-fra.com

Définition de l'en-tête d'autorisation de HttpClient

J'ai un client HTTP que j'utilise pour utiliser une API REST. Cependant, j'ai des difficultés à configurer l'en-tête Authorization. Je dois définir l'en-tête sur le jeton que j'ai reçu en effectuant ma demande OAuth .

httpClient.DefaultRequestHeaders.Authorization = new Credential(OAuth.token);

Cependant, la classe Credential n’existe pas dans WinRT. Quelqu'un a une idée sur la manière de définir l'en-tête d'autorisation?

313
Stephen Hynes

Donc, la façon de le faire est la suivante,

httpClient.DefaultRequestHeaders.Authorization =
    new AuthenticationHeaderValue("Bearer", "Your Oauth token");
583
Stephen Hynes
request.DefaultRequestHeaders.Authorization = 
    new AuthenticationHeaderValue(
        "Basic", 
        Convert.ToBase64String(
            System.Text.ASCIIEncoding.ASCII.GetBytes(
                string.Format("{0}:{1}", "yourusername", "yourpwd"))));
228
TheWhiteRabbit

Je cherche un bon moyen de régler ce problème et je regarde la même question. Espérons que cette réponse aidera tous ceux qui ont le même problème à s’aimer.

using (var client = new HttpClient())
{
    var url = "https://www.theidentityhub.com/{tenant}/api/identity/v1";
    client.DefaultRequestHeaders.Add("Authorization", "Bearer " + accessToken);
    var response = await client.GetStringAsync(url);
    // Parse JSON response.
    ....
}

référence de https://www.theidentityhub.com/hub/Documentation/CallTheIdentityHubApi

61
Willie Cheng

Je suis d'accord avec la réponse de TheWhiteRabbit mais si vous avez beaucoup d'appels utilisant HttpClient, le code semble un peu répétitif à mon avis. 

Je pense qu'il y a 2 façons d'améliorer la réponse un peu.

Créez une classe d'assistance pour créer le client:

public static class ClientHelper
{
    // Basic auth
    public static HttpClient GetClient(string username,string password)
    {
            var authValue = new AuthenticationHeaderValue("Basic", Convert.ToBase64String(Encoding.UTF8.GetBytes($"{username}:{password}")));

            var client = new HttpClient(){
                DefaultRequestHeaders = { Authorization = authValue}
                //Set some other client defaults like timeout / BaseAddress
            };
            return client;
    }

    // Auth with bearer token
    public static HttpClient GetClient(string token)
    {
            var authValue = new AuthenticationHeaderValue("Bearer", token);

            var client = new HttpClient(){
                DefaultRequestHeaders = { Authorization = authValue}
                //Set some other client defaults like timeout / BaseAddress
            };
            return client;
    }
}

Utilisation:

using(var client = ClientHelper.GetClient(username,password))
{
    //Perform some http call
}

using(var client = ClientHelper.GetClient(token))
{
    //Perform some http call
}

Créer une méthode d'extension:

Ne gagne pas un prix de beauté mais fonctionne très bien :)

    public static class HttpClientExtentions
    {
        public static AuthenticationHeaderValue ToAuthHeaderValue(this string username, string password)
        {
            return new AuthenticationHeaderValue("Basic",
        Convert.ToBase64String(
            System.Text.Encoding.ASCII.GetBytes(
                $"{username}:{password}")));
        }
    }

Utilisation:

using (var client = new HttpClient())
{
    client.DefaultRequestHeaders.Authorization = _username.ToAuthHeaderValue(_password); 
}

Encore une fois, je pense que 2 options ci-dessus rendent le client qui utilise l'instruction un peu moins répétitif. N'oubliez pas qu'il est préférable de réutiliser HttpClient si vous effectuez plusieurs appels http, mais je pense que c'est un peu hors de portée pour cette question.

33
Florian Schaal

Comme il s’agit d’une bonne pratique de réutiliser l’instance HttpClient}, pour problèmes de performances et d’épuisement des ports, et parce qu’aucune des réponses ne donne cette solution (et même vous mène vers de mauvaises pratiques :(), Je mets ici un lien vers la réponse que j'ai faite à une question similaire:

https://stackoverflow.com/a/40707446/717372

Quelques sources pour bien utiliser HttpClient:

25
Philippe

Pour définir l'authentification de base avec C # HttpClient. Le code suivant fonctionne pour moi. 

   using (var client = new HttpClient())
        {
            var webUrl ="http://localhost/saleapi/api/";
            var uri = "api/sales";
            client.BaseAddress = new Uri(webUrl);
            client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
            client.DefaultRequestHeaders.ConnectionClose = true;

            //Set Basic Auth
            var user = "username";
            var password = "password";
            var base64String =Convert.ToBase64String( Encoding.ASCII.GetBytes($"{user}:{password}"));
            client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Basic",base64String);

            var result = await client.PostAsJsonAsync(uri, model);
            return result;
        }
9
LENG UNG

Voici comment je l'ai fait:

using (HttpClient httpClient = new HttpClient())
{
   Dictionary<string, string> tokenDetails = null;
   var messageDetails = new Message { Id = 4, Message1 = des };
   HttpClient client = new HttpClient();
   client.BaseAddress = new Uri("http://localhost:3774/");
   var login = new Dictionary<string, string>
       {
           {"grant_type", "password"},
           {"username", "[email protected]"},
           {"password", "lopzwsx@23"},
       };
   var response = client.PostAsync("Token", new FormUrlEncodedContent(login)).Result;
   if (response.IsSuccessStatusCode)
   {
      tokenDetails = JsonConvert.DeserializeObject<Dictionary<string, string>>(response.Content.ReadAsStringAsync().Result);
      if (tokenDetails != null && tokenDetails.Any())
      {
         var tokenNo = tokenDetails.FirstOrDefault().Value;
         client.DefaultRequestHeaders.Add("Authorization", "Bearer " + tokenNo);
         client.PostAsJsonAsync("api/menu", messageDetails)
             .ContinueWith((postTask) => postTask.Result.EnsureSuccessStatusCode());
      }
   }
}

Cette vidéo de you-tube m'aide beaucoup. Veuillez le vérifier . https://www.youtube.com/watch?v=qCwnU06NV5Q

7
Dayan

Utilisez l'autorisation de base et les paramètres Json.

using (HttpClient client = new HttpClient())
                    {
                        var request_json = "your json string";

                        var content = new StringContent(request_json, Encoding.UTF8, "application/json");

                        var authenticationBytes = Encoding.ASCII.GetBytes("YourUsername:YourPassword");

                        client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Basic",
                               Convert.ToBase64String(authenticationBytes));
                        client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));

                        var result = await client.PostAsync("YourURL", content);

                        var result_string = await result.Content.ReadAsStringAsync();
                    }
5
MohammadSoori

Option UTF8

request.DefaultRequestHeaders.Authorization = 
new AuthenticationHeaderValue(
    "Basic", Convert.ToBase64String(
        System.Text.Encoding.UTF8.GetBytes(
           $"{yourusername}:{yourpwd}")));
4
romelmederos

Utilisation de la classe AuthenticationHeaderValue de System.Net.Http Assembly

public AuthenticationHeaderValue(
    string scheme,
    string parameter
)

nous pouvons définir ou mettre à jour l'en-tête Authorization existant pour notre httpclient comme ceci:

httpclient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", TokenResponse.AccessToken);
3
Fusion

6 ans plus tard, mais en ajoutant ceci au cas où cela pourrait aider quelqu'un.

https://www.codeproject.com/Tips/996401/Authenticate-WebAPIs-with-Basic-and-Windows-Authen

var authenticationBytes = Encoding.ASCII.GetBytes("<username>:<password>");
using (HttpClient confClient = new HttpClient())
{
  confClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Basic", 
         Convert.ToBase64String(authenticationBytes));
  confClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue(Constants.MediaType));  
  HttpResponseMessage message = confClient.GetAsync("<service URI>").Result;
  if (message.IsSuccessStatusCode)
  {
    var inter = message.Content.ReadAsStringAsync();
    List<string> result = JsonConvert.DeserializeObject<List<string>>(inter.Result);
  }
}
1
MPJ567

cela pourrait fonctionner si vous recevez un json ou un xml du service et que cela peut vous donner une idée de la manière dont fonctionnent les en-têtes et le type T, si vous utilisez la fonction MakeXmlRequest (mettre les résultats dans xmldocumnet) et MakeJsonRequest (placez le json dans la classe de votre choix qui a la même structure que la réponse json) de la manière suivante

/*-------------------------example of use-------------*/
MakeXmlRequest<XmlDocument>("your_uri",result=>your_xmlDocument_variable =     result,error=>your_exception_Var = error);

MakeJsonRequest<classwhateveryouwant>("your_uri",result=>your_classwhateveryouwant_variable=result,error=>your_exception_Var=error)
/*-------------------------------------------------------------------------------*/


public class RestService
{
    public void MakeXmlRequest<T>(string uri, Action<XmlDocument> successAction, Action<Exception> errorAction)
    {
        XmlDocument XMLResponse = new XmlDocument();
        string wufooAPIKey = ""; /*or username as well*/
        string password = "";
        StringBuilder url = new StringBuilder();
        url.Append(uri);
        HttpWebRequest request = (HttpWebRequest)HttpWebRequest.Create(url.ToString());
        string authInfo = wufooAPIKey + ":" + password;
        authInfo = Convert.ToBase64String(Encoding.Default.GetBytes(authInfo));
        request.Timeout = 30000;
        request.KeepAlive = false;
        request.Headers["Authorization"] = "Basic " + authInfo;
        string documento = "";
        MakeRequest(request,response=> documento = response,
                            (error) =>
                            {
                             if (errorAction != null)
                             {
                                errorAction(error);
                             }
                            }
                   );
        XMLResponse.LoadXml(documento);
        successAction(XMLResponse);
    }



    public void MakeJsonRequest<T>(string uri, Action<T> successAction, Action<Exception> errorAction)
    {
        string wufooAPIKey = "";
        string password = "";
        StringBuilder url = new StringBuilder();
        url.Append(uri);
        HttpWebRequest request = (HttpWebRequest)HttpWebRequest.Create(url.ToString());
        string authInfo = wufooAPIKey + ":" + password;
        authInfo = Convert.ToBase64String(Encoding.Default.GetBytes(authInfo));
        request.Timeout = 30000;
        request.KeepAlive = false;
        request.Headers["Authorization"] = "Basic " + authInfo;
       // request.Accept = "application/json";
      //  request.Method = "GET";
        MakeRequest(
           request,
           (response) =>
           {
               if (successAction != null)
               {
                   T toReturn;
                   try
                   {
                       toReturn = Deserialize<T>(response);
                   }
                   catch (Exception ex)
                   {
                       errorAction(ex);
                       return;
                   }
                   successAction(toReturn);
               }
           },
           (error) =>
           {
               if (errorAction != null)
               {
                   errorAction(error);
               }
           }
        );
    }
    private void MakeRequest(HttpWebRequest request, Action<string> successAction, Action<Exception> errorAction)
    {
        try{
            using (var webResponse = (HttpWebResponse)request.GetResponse())
            {
                using (var reader = new StreamReader(webResponse.GetResponseStream()))
                {
                    var objText = reader.ReadToEnd();
                    successAction(objText);
                }
            }
        }catch(HttpException ex){
            errorAction(ex);
        }
    }
    private T Deserialize<T>(string responseBody)
    {
        try
        {
            var toReturns = JsonConvert.DeserializeObject<T>(responseBody);
             return toReturns;
        }
        catch (Exception ex)
        {
            string errores;
            errores = ex.Message;
        }
        var toReturn = JsonConvert.DeserializeObject<T>(responseBody);
        return toReturn;
    }
}
}
0
Jesus Cañedo

J'étais en train de définir le jeton porteur httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue ("Bearer", jeton);

Cela fonctionnait sur un terminal, mais pas sur un autre. Le problème était que j'avais des minuscules "b" sur "porteur". Après le changement maintenant, cela fonctionne pour les deux api que je frappe. Une chose si facile à manquer si vous ne le considérez même pas comme l'une des meules de foin à rechercher l'aiguille.

Assurez-vous d'avoir "porteur" - avec le capital.

0
Alan Ball