web-dev-qa-db-fra.com

401- Authentification non autorisée en utilisant REST API Dynamics CRM avec Azure AD

J'essaie d'accéder à une API REST de Dynamics CRM Online avec l'authentification Azure AD oAuth 2. Pour ce faire, j'ai suivi les étapes suivantes:

- J'ai enregistré une application Web et/ou une API Web dans Azure.
- Configuration des autorisations sur Dynamics CRM pour disposer d'autorisations déléguées "Accéder à CRM Online en tant qu'utilisateur d'organisation"
- Et créé une clé avec une expiration d'un an et conservait l'ID de client généré .

Après la configuration de l'application Web sur Azure, j'ai créé une application console dans .NET/C # qui utilise ADAL pour effectuer une demande simple, dans ce cas, pour récupérer une liste de comptes:

    class Program
{
    private static string ApiBaseUrl = "https://xxxxx.api.crm4.dynamics.com/";
    private static string ApiUrl = "https://xxxxx.api.crm4.dynamics.com/api/data/v8.1/";
    private static string ClientId = "2a5dcdaf-2036-4391-a3e5-9d0852ffe3f2";
    private static string AppKey = "symCaAYpYqhiMK2Gh+E1LUlfxbMy5X1sJ0/ugzM+ur0=";

    static void Main(string[] args)
    {
        AuthenticationParameters ap = AuthenticationParameters.CreateFromResourceUrlAsync(new Uri(ApiUrl)).Result;

        var clientCredential = new ClientCredential(ClientId, AppKey);

        var authenticationContext = new AuthenticationContext(ap.Authority);
        var authenticationResult = authenticationContext.AcquireToken(ApiBaseUrl, clientCredential);

        var httpClient = new HttpClient();
        httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", authenticationResult.AccessToken);

        var result = httpClient.GetAsync(Path.Combine(ApiUrl, "accounts")).Result;         
    }
}

Je récupère un jeton d'accès avec succès, mais lorsque j'essaie d'effectuer une demande http à CRM, je reçois toujours un 401 - Code d'état non autorisé . Qu'est-ce que je rate?

12
AndreCavaca

1 an et 2 mois plus tard, ce même code fonctionne parfaitement. Comme beaucoup l'ont indiqué, Dynamics 365 a commencé à prendre en charge l'authentification serveur à serveur (S2S) entre-temps. La seule étape que je devais faire que je ne connaissais pas à l'époque était de créer un utilisateur d'application . Pour plus d'informations sur la manière de rendre cette authentification efficace, consultez ce site Web: https://msdn.Microsoft.com /en-us/library/mt790170.aspx

4
AndreCavaca

Merci à tous pour vos réponses. J'ai finalement réussi à accéder à l'API OData de Dynamics CRM avec ADAL 3.

Etant donné que de nombreuses personnes rencontrent encore des problèmes, suivez les étapes ci-après:

Enregistrement de l'application

  1. Connectez-vous à portal.Azure.com à l'aide de votre utilisateur administrateur Office 365 de votre abonnement Dynamics CRM.

  2. Accédez à Inscriptions Azure Active Director\App et ajoutez des inscriptions Nouvelle application.

  3. Entrez "Nom" et "URL de connexion", l'URL peut être n'importe quoi ( https: // localhost par exemple)

  4. Sélectionnez l'application enregistrée que vous venez de créer, accédez à Paramètres\Clés

  5. Entrez une description de la clé, cliquez sur Enregistrer et copiez la valeur (et conservez-la, vous en aurez besoin ultérieurement). Copiez également l'ID d'application de l'application enregistrée.

  6. Accédez à "Autorisations requises", cliquez sur Ajouter, sélectionnez "Dynamics CRM Online" puis cochez la case "Accéder à CRM Online en tant qu'utilisateur d'organisation".

Ces étapes permettent à une application cliente d'accéder à Dynamics CRM à l'aide de l'ID d'application et du secret client que vous avez créés à l'étape 5 . Votre application cliente peut désormais être authentifiée contre Azure AD avec le droit d'accéder à CRM Online. . Cependant, CRM Online ne connaît pas cette "application client" ou cet "utilisateur". L'API CRM répondra 401 si vous essayez d'y accéder. 

Ajouter un utilisateur d'application CRM

Pour informer CRM de "l'application cliente" ou de "l'utilisateur", vous devez ajouter un utilisateur d'application. 

  1. Allez dans CRM\Rôles de sécurité, créez un nouveau rôle de sécurité ou copiez simplement le rôle "Administrateur système".

  2. Allez dans CRM\Paramètres\Sécurité\Utilisateurs, créez un nouvel utilisateur, changez le formulaire en "Utilisateur de l'application".

  3. Entrez les champs obligatoires avec l'ID d'application que vous avez à l'étape précédente. Une fois enregistré, CRM renseignera automatiquement l'ID d'objet Azure AD et l'URI.

  4. Ajoutez l'utilisateur au rôle de sécurité créé à l'étape précédente.

Vous devriez maintenant pouvoir accéder à l'API CRM à l'aide de HttpClient et ADAL à l'aide de l'exemple de code ci-dessous:

var ap = await AuthenticationParameters.CreateFromResourceUrlAsync(
                new Uri("https://*****.api.crm6.dynamics.com/api/data/v9.0/"));

String authorityUrl = ap.Authority;
String resourceUrl = ap.Resource;

var authContext = new AuthenticationContext(authorityUrl);
var clientCred = new ClientCredential("Application ID", "Client Secret");
var test = await authContext.AcquireTokenAsync(resourceUrl, clientCred);

Console.WriteLine(test.AccessToken);

using (var client = new HttpClient())
{
    client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", test.AccessToken);

    var response = await client.GetAsync("https://*****.api.crm6.dynamics.com/api/data/v9.0/contacts");
    var contacts = await response.Content.ReadAsStringAsync();

    Console.WriteLine(contacts);
}
6
Van Nguyen

Je vous conseillerais de jeter un œil à l'authentification serveur à serveur (S2S), qui a été ajoutée à Dynamics 365 dans la dernière version.

En utilisant S2S, vous n’avez pas besoin d’une licence Dynamics 365 payante. Plutôt que les informations d'identification de l'utilisateur, l'application est authentifiée en fonction d'un principal de service identifié par une valeur d'ID d'objet Azure AD stockée dans l'enregistrement d'utilisateur de l'application Dynamics 365.

Plus d'informations peuvent être trouvées ici: https://msdn.Microsoft.com/en-us/library/mt790168.aspxhttps://msdn.Microsoft.com/en- us/library/mt790170.aspx

3
Hendry Timmer

Votre ID client, AppKey from Azure, donc ap.Authority doit être https://login.microsoftonline.com/tenantid dans var authenticationContext = new AuthenticationContext(ap.Authority);

0
Lily_user4045

Je ne pense pas que vous serez en mesure de vous débrouiller en fournissant des informations d'identification d'utilisateur à au moins un type de "compte d'intégration". Vous pouvez éviter un flux OAUTH popup/redirection plus traditionnel avec les éléments suivants:

using Microsoft.IdentityModel.Clients.ActiveDirectory;
using System;
using System.IO;
using System.Net;

namespace ConsoleApplication2
{
    class Program
    {
        private static string API_BASE_URL = "https://<CRM DOMAIN>/";
        private static string API_URL = "https://<CRM DOMAIN>/api/data/v8.1/";
        private static string CLIENT_ID = "<CLIENT ID>";

        static void Main(string[] args)
        {
            var userCredential = new UserCredential("<USERNAME>", "<PASSWORD>");
            var authContext = new AuthenticationContext("https://login.windows.net/common", false);
            var result = authContext.AcquireToken(API_BASE_URL, CLIENT_ID, userCredential);

            var httpClient = HttpWebRequest.CreateHttp(Path.Combine(API_URL, "accounts"));
            httpClient.Headers.Add(HttpRequestHeader.Authorization, "Bearer:" + result.AccessToken);
            using (var sr = new StreamReader(httpClient.GetResponse().GetResponseStream()))
            {
                Console.WriteLine(sr.ReadToEnd());
            }

            Console.ReadLine();
        }
    }
}

Remarque: J'utilise une version antérieure d'ADAL ( 2.19.208020213 ) car il apparaît que le paramètre password a été retiré du constructeur UserCredential.

EDIT: CRM prend désormais en charge Authentification serveur à serveur qui vous permet de créer un utilisateur d'application.

0
Matt Dearing

Vous aurez peut-être besoin d'une configuration d'utilisateur d'application dans CRM adaptée à votre application Azure: https://msdn.Microsoft.com/en-us/library/mt790170.aspx

Bien que vous puissiez configurer votre jeton de support en C #, la requête Web adressée à la ressource CRM peut échouer en raison d'autorisations de niveau CRM.

0
user14114