控制台程序(C#)不弹出登录窗口连接到Dynamics CRM Online的Web API

微软动态CRM专家罗勇 ,回复331或者20190505可方便获取本文,同时可以在第一间得到我发布的最新博文信息,follow me!

我之前的文章 控制台程序(C#)不弹出认证窗口连接到Dynamics CRM Online的Web API 发现不好用了,我在stackoverflow上找到了类似的答案,由 IntegerWolf 提供的问题 Using ADAL C# as Confidential User /Daemon Server /Server-to-Server - 401 Unauthorized 的答案。

首先登录 https://portal.azure.com 注册一个app,如下图所示新建:

 

Name取得有意义即可,Redirect URI得值暂时用不上,然后点击 Register 按钮。

 

创建成功后将Application (client) ID 和Directory (tenant) ID 复制出来备用。

 

然后点击左边的 Certificates & secrets ,再点击右边的 New client secret按钮。

 

 直接点击 Add 按钮。

 

 将自动产生的 client secret 复制出来备用。

 

然后再点击左边的 API permissions ,点击右边的 Add a permission。

 

将Dynamics CRM Online的如下权限添加上:

再点击下 Grant admin consent for Consoto 按钮,在提示中点击Yes,等待操作完成。

 

下面就是代码部分了:

using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.IO;
using System.Net.Http;
using System.Net.Http.Headers;
using System.Runtime.Serialization.Json;
using System.Threading.Tasks;

namespace UsingWebAPI
{
    public class AuthenticationResponse
    {
        public string token_type { get; set; }
        public string scope { get; set; }
        public int expires_in { get; set; }
        public int expires_on { get; set; }
        public int not_before { get; set; }
        public string resource { get; set; }
        public string access_token { get; set; }
        public string refresh_token { get; set; }
        public string id_token { get; set; }
    }

    public class Account
    {
        public string name { get; set; }

        public string telephone1 { get; set; }
    }
    class Program
    {

        static string resourceUrl = "https://crm773088.api.crm.dynamics.com/";
        static string clientId = "87ca6bd8-3e66-49bd-a756-9c4d86a9ff1a";
        static string clientSecret = "iU0@eOCT*Q0r9CGjWdMmJla";
        static string tenantId = "79f34dea-50b2-4acf-80e9-700391c4cf83";
        static string userName = "admin@CRM773088.onmicrosoft.com";
        static string password = "Pas91";
        static void Main(string[] args)
        {
            GetAuthenticationResponse();
            Console.ReadKey();
        }

        private static async void GetAuthenticationResponse()
        {
            List<KeyValuePair<string, string>> vals = new List<KeyValuePair<string, string>>();

            vals.Add(new KeyValuePair<string, string>("client_id", clientId));
            vals.Add(new KeyValuePair<string, string>("resource", resourceUrl));
            vals.Add(new KeyValuePair<string, string>("username", userName));
            vals.Add(new KeyValuePair<string, string>("password", password));
            vals.Add(new KeyValuePair<string, string>("grant_type", "password"));
            vals.Add(new KeyValuePair<string, string>("client_secret", clientSecret));
            string url = string.Format("https://login.windows.net/{0}/oauth2/token", tenantId);

            using (HttpClient httpClient = new HttpClient())
            {
                httpClient.DefaultRequestHeaders.Add("Cache-Control", "no-cache");
                HttpContent content = new FormUrlEncodedContent(vals);
                HttpResponseMessage hrm = httpClient.PostAsync(url, content).Result;

                AuthenticationResponse authenticationResponse = null;
                if (hrm.IsSuccessStatusCode)
                {
                    Stream data = await hrm.Content.ReadAsStreamAsync();
                    DataContractJsonSerializer serializer = new DataContractJsonSerializer(typeof(AuthenticationResponse));
                    authenticationResponse = (AuthenticationResponse)serializer.ReadObject(data);
                    DataOperations(authenticationResponse);
                }
                else
                {
                    Console.WriteLine("Error." + hrm.ReasonPhrase);
                }
            }
        }

        private static async Task DataOperations(AuthenticationResponse authResult)
        {
            using (HttpClient httpClient = new HttpClient())
            {
                httpClient.BaseAddress = new Uri("https://crm773088.api.crm.dynamics.com/");
                httpClient.Timeout = new TimeSpan(0, 2, 0); //2 minutes
                httpClient.DefaultRequestHeaders.Add("OData-MaxVersion", "4.0");
                httpClient.DefaultRequestHeaders.Add("OData-Version", "4.0");
                httpClient.DefaultRequestHeaders.Add("Cache-Control", "no-cache");
                httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
                httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", authResult.access_token);

                Account account = new Account();
                account.name = "Test Account";
                account.telephone1 = "555-555";

                string content = String.Empty;
                content = JsonConvert.SerializeObject(account, new JsonSerializerSettings() { DefaultValueHandling = DefaultValueHandling.Ignore });
                HttpRequestMessage request = new HttpRequestMessage(HttpMethod.Post, "api/data/v9.1/accounts");
                request.Content = new StringContent(content);
                request.Content.Headers.ContentType = MediaTypeHeaderValue.Parse("application/json");
                HttpResponseMessage response = await httpClient.SendAsync(request);
                if (response.IsSuccessStatusCode)
                {
                    Console.WriteLine("Account '{0}' created.", account.name);
                }
                else
                {
                    throw new Exception(String.Format("Failed to create account '{0}', reason is '{1}'."
                      , account.name
                      , response.ReasonPhrase));
                }
            }
        }
    }
}

 

获取access token的方法用如下的Postman请求模拟也可以获取到。

 

posted @ 2019-05-05 01:50  微软MVP(15-18)罗勇  阅读(991)  评论(0编辑  收藏  举报