因此,首先,我使用下面的博客文章来帮助我将CSX Azure Function转换为预编译的类库-https://blogs.msdn.microsoft.com/appserviceteam/2017/03/16/publishing-a-net-class-library-as-a-function-app/?utm_source=Direct

我已经知道它应该可以工作了,但是作为一个预编译的函数,它在SetBearerToken(在System.Net.Http.HttpClientExtensions中)上引发了“未找到方法”异常,但是它没有在CSX版本中找到此方法的任何问题。这是完整的错误:

Exception while executing function: Functions.notifications-queue-triggerMicrosoft.Azure.WebJobs.Host.FunctionInvocationException : Exception while executing function: Functions.notifications-queue-trigger ---> System.Reflection.TargetInvocationException : Exception has been thrown by the target of an invocation. ---> System.MissingMethodException : Method not found: 'Void System.Net.Http.HttpClientExtensions.SetBearerToken(System.Net.Http.HttpClient, System.String)'.

该代码在预编译函数和CSX脚本之间几乎是相同的(显然不是必需的区别)。

我在这里想念什么?当它作为CSX脚本编写时没有问题时,为什么在System.Net.Http.HttpClientExtensions中为SetBearerToken抛出“未找到方法”异常?任何帮助表示赞赏。

这是我作为CSX脚本的功能,可以正常工作:

#r "IdentityModel.dll"
#r "Sorbet.DataTransferObjects.dll"
#r "Newtonsoft.Json"

using System;
using System.Text;
using System.Threading.Tasks;
using System.Net.Http;

using IdentityModel.Client;
using Newtonsoft.Json;
using Sorbet.DataTransferObjects;

public static void Run(NotificationDto myQueueItem, TraceWriter log)
{
    log.Info($"C# ServiceBus queue trigger function processed message");
    TokenResponse idToken;
    using (var tokenClient = new TokenClient("https://myidserver", "myclientid", "myclientsecret"))
    {
        var response = tokenClient.RequestClientCredentialsAsync("myscope");
        idToken = response.Result;
        log.Info($"Access token retrieved : {idToken.AccessToken}");
    }

    using (var apiClient = new HttpClient())
    {
        var apiUrl = "https://myapiurl/";
        var endpoint = "myendpoint";
        string data = JsonConvert.SerializeObject(myQueueItem);
        log.Info($"Hitting API...");

        apiClient.SetBearerToken(idToken.AccessToken);
        var response = apiClient.PostAsync($"{apiUrl}{endpoint}", new StringContent(data, Encoding.UTF8, "application/json")).Result;
    }
}


这是我作为C#类的函数,这会在SetBearerToken调用上引发上述错误:

using System;
using System.Text;
using System.Threading.Tasks;
using System.Net.Http;

using IdentityModel.Client;
using Microsoft.Azure.WebJobs.Host;
using Newtonsoft.Json;
using Sorbet.DataTransferObjects;

namespace FunctionsClassLibTest
{
    public class NotificationQueueTrigger
    {
        public static void Run(NotificationDto myQueueItem, TraceWriter log)
        {
            log.Info($"C# ServiceBus queue trigger function processed message");
            TokenResponse idToken;
            using (var tokenClient = new TokenClient("https://myidserver", "myclientid", "myclientsecret"))
            {
                var response = tokenClient.RequestClientCredentialsAsync("myscope");
                idToken = response.Result;
                log.Info($"Access token retrieved : {idToken.AccessToken}");
            }

            using (var apiClient = new HttpClient())
            {
                var apiUrl = "https://myapiurl";
                var endpoint = "myendpoint";
                string data = JsonConvert.SerializeObject(myQueueItem);
                log.Info($"Hitting API...");

                apiClient.SetBearerToken(idToken.AccessToken);
                var response = apiClient.PostAsync($"{apiUrl}{endpoint}", new StringContent(data, Encoding.UTF8, "application/json")).Result;
            }
        }
    }
}


这是我的预编译函数的function.json文件(CSX几乎相同,但只有绑定部分)

{
  "scriptFile": "..\\bin\\FunctionsClassLibTest.dll",
  "entryPoint": "FunctionsClassLibTest.NotificationQueueTrigger.Run",
  "bindings": [
    {
      "name": "myQueueItem",
      "type": "serviceBusTrigger",
      "direction": "in",
      "queueName": "notifications",
      "connection": "dev-bus",
      "accessRights": "manage"
    }
  ],
  "disabled": false
}

最佳答案

好的,所以我已经找到了解决方案。问题是我认为刚开始时可能在IdentityModel库中。我被错误抛出的命名空间所吸引,使我不得不继续追赶几个小时。实际上,在IdentityModel库中定义了HttpClient的扩展。

确切知道问题出在哪里,我查看了扩展,然后用该扩展方法apiClient.SetBearerToken("myBearerToken");中使用的代码替换了apiClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", "myBearerToken");行,现在这在我的预编译函数中起作用了。

这并不能回答为什么它在CSX中起作用,而不能在预编译函数中起作用的问题。如果有人对为什么会有任何想法,我将非常有兴趣知道!我知道导入IdentityModel库不是问题,因为我使用它来从我的ID服务器获取令牌,并且可以正常工作,因此它必须是扩展方法特有的。有问题的扩展方法可以在这里看到-https://github.com/IdentityModel/IdentityModel/blob/master/source/IdentityModel.Shared/Client/HttpClientExtensions.cs

关于c# - 在HttpClientExtensions.SetBearerToken使用上预编译的Azure函数抛出错误,CSX不,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/43367113/

10-10 23:12