【问题标题】:Making Microsoft Graph API call with Hangfire使用 Hangfire 进行 Microsoft Graph API 调用
【发布时间】:2021-02-19 16:19:16
【问题描述】:

我正在努力使用 Hangfire 后台作业进行图形 API 调用,因为我认为 HttpContext 在进行调用时为空,我不知道如何解决这个问题。

// 设置作业延迟触发

BackgroundJob.Schedule(() => this.HangfireTest("test@gmail.com", false), TimeSpan.FromSeconds(20));

// 调用graph api,返回结果为'Not yet computed'

var userInfo = this.graphServiceClient.Me.Request().Select(Info.Fields).GetAsync();

我尝试过传入上下文,但这不起作用。不知道如何解决这个问题。谢谢!

【问题讨论】:

    标签: c# microsoft-graph-api hangfire


    【解决方案1】:

    这是一个适用于我的 ASP.Net Core 3.1 MVC 原型实现。我在寻找解决方案时也遇到了很多问题,因此在这里发布。我已经编辑了一些代码,以便更容易阅读和删除解决此问题所不需要的臃肿。

    请注意,该方法是从 GraphAPI 检索访问令牌并将其传递给后台作业,创建一个新的独立 GraphClient 实例并添加包含访问令牌的所需承载头。

    在 startup.cs 中,EnableTokenAcquisition 允许在控制器中检索访问令牌。

    services.AddAuthentication(OpenIdConnectDefaults.AuthenticationScheme)
        .AddMicrosoftIdentityWebApp(this.Configuration.GetSection("AzureAd"))
        .EnableTokenAcquisitionToCallDownstreamApi(initialScopes)
        .AddMicrosoftGraph(this.Configuration.GetSection("DownstreamApi"))
        .AddInMemoryTokenCaches();
    

    控制器初始化...

    using Microsoft.Graph;
    using Microsoft.Identity.Web;
    
    private readonly GraphServiceClient graphServiceClient;
    private readonly ITokenAcquisition tokenAcquisition = null;
    
    public HomeController(ILogger<HomeController> logger, IConfiguration iconfiguration, GraphServiceClient graphServiceClient, ITokenAcquisition tokenAcquisition)
    {
        this.graphServiceClient = graphServiceClient;
        this.tokenAcquisition = tokenAcquisition;
    }
    

    计划作业控制器操作

    public IActionResult ScheduleJob(BackgroundJobsViewModel model)
    {
        try
        {
            string accessToken = string.Empty;
    
            try
            {
                accessToken = Task.Run(async () => await this.tokenAcquisition.GetAccessTokenForUserAsync(scopeList)).Result;
            }
            catch (MicrosoftIdentityWebChallengeUserException ex)
            {
                Task.Run(async () => await this.tokenAcquisition.ReplyForbiddenWithWwwAuthenticateHeaderAsync(scopeList, ex.MsalUiRequiredException));
            }
            catch (Microsoft.Identity.Client.MsalUiRequiredException ex)
            {
                Task.Run(async () => await this.tokenAcquisition.ReplyForbiddenWithWwwAuthenticateHeaderAsync(scopeList, ex));
            }
    
            if (!string.IsNullOrEmpty(accessToken))
            {
    
                // Recurring Job.
                RecurringJob.AddOrUpdate(job.JobName, () => UpdateUsersBackroundJob.UpdateUsers(this.currentUser.Account, accessToken), $"{seconds} {minutes} {hours} {day} {month} {week}");
            }
            else
            {
                return this.View("BackgroundJobs", model);
            }
        }
        catch (Exception ex)
        {
            var errorModel = this.HandleException(ex);
            return this.View("Error", errorModel);
        }
    }
    

    后台作业类和方法...注意 Info.Fields 我没有显示。

    using Microsoft.Graph;
    using Microsoft.Identity.Web;
    
    /// <summary>
    /// Class to encapsulate the background job to update users.
    /// </summary>
    public class UpdateUsersBackroundJob
    {
        /// <summary>
        /// Gets or sets the Graph Client.
        /// </summary>
        private static GraphServiceClient GraphClient { get; set; }
    
        public static void UpdateUsers(string upnName, string graphApiAccessToken)
        {
            if (string.IsNullOrEmpty(graphApiAccessToken))
            {
                throw new ApplicationException("Cannot run the update users background job without specifying an access token first.");
            }
    
            // Create our own new graph client using the provided token.
            GraphClient = new GraphServiceClient(new DelegateAuthenticationProvider((requestMessage) =>
            {
                requestMessage.Headers.Authorization = new AuthenticationHeaderValue("bearer", graphApiAccessToken);
                return Task.FromResult(0);
            }));
            
            try
            {
    
                    // Update DB User data from GraphAPI Azure AD
                    var userInfo = Task.Run(async () => await GraphClient.Me.Request().Select(Info.Fields).GetAsync()).Result;
                    
                    ...do something with userInfo in application.
                }
                catch
                {
                    ...Handle exception.
                }
            }
        }
    }
    

    【讨论】:

      猜你喜欢
      • 2020-07-28
      • 1970-01-01
      • 2019-11-11
      • 1970-01-01
      • 2020-04-26
      • 1970-01-01
      • 2019-01-10
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多