如何使用Azure移动应用程序后端从Microsoft Graph获取经过身份验证的用户的用户信息?

时间:2017-11-15 02:06:48

标签: c# azure-mobile-services microsoft-graph

使用我的应用程序的后端,我试图从已经过身份验证的用户的Microsoft Graph中捕获信息,然后将该用户添加到数据库。身份验证似乎正常工作,但用户永远不会添加到数据库中。我真的很困惑。我已经广泛研究了在线文档,但一直无法找到解决方案。如果我可以告诉用户属性是否已经填充,我可以弄清楚发生了什么,但由于代码在服务器上运行,我无法做到这一点。 (我已尝试远程调试,但无法成功设置断点。)有人能告诉我在下面的代码中我做错了什么吗?

class MicrosoftAccountInfo
{
    public string id { get; set; }
    public string displayName { get; set; }
    public string mail { get; set; }
}

[MobileAppController]
public class MicrosoftAccountController : ApiController
{
    MicrosoftAccountCredentials credentials;
    string msRequestUrl;
    MyAppContext context;
    EntityDomainManager<User> domainManager;

    // GET api/<controller>
    public async Task<User> Get()
    {
        if (credentials == null)
        {
            credentials = await this.User.GetAppServiceIdentityAsync<MicrosoftAccountCredentials>(this.Request);
        }         

        msRequestUrl = "https://graph.microsoft.com/v1.0/me/?$select=id,displayName,mail";

        var client = new System.Net.Http.HttpClient();
        var headerValue = "Bearer" + credentials.AccessToken;
        client.DefaultRequestHeaders.Add("Authorization", headerValue);
        var resp = await client.GetAsync(msRequestUrl);
        resp.EnsureSuccessStatusCode();
        var msInfo = await resp.Content.ReadAsStringAsync();

        MicrosoftAccountInfo info = JsonConvert.DeserializeObject<MicrosoftAccountInfo>(msInfo);
        context = new MyAppContext();
        domainManager = new EntityDomainManager<User>(context, Request);
        var user = context.Users.FirstOrDefault(u => u.Email == info.mail);
        if (user == null)
        {
            user = new DataObjects.User { Email = info.mail, UserName = info.displayName, ProviderId = info.id };
            await domainManager.InsertAsync(user);
        }
        else if (string.IsNullOrEmpty(user.ProviderId))
        {
            user.UserName = info.displayName;
            user.ProviderId = info.id;
            await context.SaveChangesAsync();
        }
        return user;
    }
}

1 个答案:

答案 0 :(得分:0)

至于为什么会失败,很难在没有实际错误消息的情况下确定。确实有很多变量/潜在的失败点。

也就是说,您可以使用Microsoft Graph .NET Client Library减少潜在故障点的数量。还有一个NuGet package可用:Install-Package Microsoft.Graph

该库将处理组成Microsoft Graph并将响应反序列化为对象。除了删除风险因素外,它还将大大简化您的代码:

Microsoft.Graph.GraphServiceClient graphClient =
    new Microsoft.Graph.GraphServiceClient(new DelegateAuthenticationProvider((requestMessage) =>
    {
        requestMessage.Headers.Authorization =
            new System.Net.Http.Headers.AuthenticationHeaderValue("bearer", "{your-access-token}");
        return Task.FromResult(0);
    }));

Microsoft.Graph.User user = await graphClient.Me.Request().GetAsync();

我还建议实施一种可以在服务器上捕获异常的监控解决方案。这有助于调试。如果您在Azure上运行,我强烈建议您使用Application Insights。除了可以自由开始之外,它实际上是一次点击一次,获得监控&#34;解。它将处理服务器的连线并为其遇到的任何异常提供报告。

请注意,您也可以将App Insights与您自己的服务器或托管在其他服务(即AWS,RackSpace)上的应用程序一起使用,但是可能需要一些手动配置。