.NET8 升级中 SignalRTrigger 函数出现空结果问题

问题描述 投票:0回答:1

您现有的项目使用什么版本的 .NET?

.NET 6

您尝试定位哪个版本的 .NET?

.NET 8

描述

嗨,

我想提出 SignalRTrigger 解决方案的问题。我和我的团队在 .NET6 项目中使用这种方法来触发一些异步操作。作为响应,我们返回一个自定义对象,指示操作是否成功。然而,在 .NET8 中,我们的 SignalRTrigger 函数始终在服务器响应中返回空结果,无论我们如何修复它。值得一提的是,在.NET8升级过程中,我们正在将功能迁移到隔离模式。

这是我们在 .NET6 中的服务器端代码:

[SignalRHub(path: "")]
public partial class MainHub : ServerlessHub<IMainHub>
{
    ...
    [FunctionName(nameof(Echo))]
    public async Task<SignalRHubActionRequest> Echo([SignalRTrigger()] InvocationContext invocationContext, string name, string message)
    {
        await Clients.Client(invocationContext.ConnectionId).Echo(name, message);
        return new SignalRHubActionRequest { SignalRHubActionStatus = SignalRHubActionStatus.Accepted };
    }
    ...
}

public class SignalRHubActionRequest
{
    public string Id { get; set; }
    public Status Status { get; set; }
}

public enum Status
{
    Success,
    Failure
}

.NET8 解决方案中此代码片段的唯一更改是 Echo 函数(在 SignalRTrigger 属性中):

[Function(nameof(Echo))]
public async Task<SignalRHubActionRequest> Echo([SignalRTrigger(nameof(MainHub), CATEGORY, nameof(Echo), "name", "message")] SignalRInvocationContext invocationContext, string name, string message)
{
    await Clients.Client(invocationContext.ConnectionId).Echo(name, $"async : {message}");
    return new SignalRHubActionRequest { SignalRHubActionStatus = SignalRHubActionStatus.Accepted };
}

这就是我们在 .NET6 中注册 SignalR 的方式:

builder.Services.Configure<SignalROptions>(o => {
    var settings = new JsonSerializerSettings()
    {
        NullValueHandling = NullValueHandling.Ignore,
        ContractResolver = new CamelCasePropertyNamesContractResolver()
    };
    settings.Converters.Add(new Newtonsoft.Json.Converters.StringEnumConverter());

    o.JsonObjectSerializer = new NewtonsoftJsonObjectSerializer(settings);
});

这是我们在.NET8中的注册:

services.AddSignalR()
        .AddNewtonsoftJsonProtocol(options =>
        {
            options.PayloadSerializerSettings = new JsonSerializerSettings
            {
                NullValueHandling = NullValueHandling.Ignore,
                ContractResolver = new CamelCasePropertyNamesContractResolver()
            };
            options.PayloadSerializerSettings.Converters.Add(new Newtonsoft.Json.Converters.StringEnumConverter());
        });

这是我们的 C# SignalR 客户端代码:

await using var connection = new HubConnectionBuilder()
    .WithAutomaticReconnect()
    .WithUrl(uriTime, options =>
    {
        options.AccessTokenProvider = () => Task.FromResult(accessToken);
    })
    .AddNewtonsoftJsonProtocol(options =>
    {
        options.PayloadSerializerSettings = new JsonSerializerSettings
        {
            NullValueHandling = NullValueHandling.Ignore,
            ContractResolver = new CamelCasePropertyNamesContractResolver()
        };
        options.PayloadSerializerSettings.Converters.Add(new Newtonsoft.Json.Converters.StringEnumConverter());
    });
await connection.StartAsync();

var result01 = await connection.InvokeAsync<SignalRHubActionRequest>("Echo", name, message);

我们检查了请求并观察到服务器端在结果属性中返回 null,无论我们尝试发送什么内容(例如,用字符串代替 SignalRHubActionRequest 或将序列化器更改为默认序列化器或 json 序列化器)。我们通过使用 NGROK 和 Fiddler 等工具证实了这一点:

我们尝试了多种方法,其中最有希望的一种是使用 SignalROutput 属性来绑定输出: [SignalROutput(HubName = nameof(MainHub), ConnectionStringSetting = "AzureSignalRConnectionString")]

这导致了服务器端错误。当我们在使用此 SignalROutput 属性时将返回类型更改为字符串时,我们遇到了不同的错误。

最终,我们从存储库下载了最新的代码库并使用了提供的示例,特别是扩展解决方案,并遇到了相同的空结果问题。

这表明问题出在库内。我们不确定这些不同错误的原因,但根据这些示例,它似乎返回错误对象。这意味着我们也可以在结果属性中返回一个对象。我们最初认为此功能已被删除,但错误表明并非如此。

此外,文档并未表明从 SignalRTrigger 函数返回对象的功能已被删除。

对此的任何帮助将不胜感激。

谢谢

项目配置和依赖

Azure 函数应用程序

<Project Sdk="Microsoft.NET.Sdk">
  <PropertyGroup>
    <TargetFramework>net8.0</TargetFramework>
    <AzureFunctionsVersion>v4</AzureFunctionsVersion>
    <OutputType>Exe</OutputType>
    <_FunctionsSkipCleanOutput>true</_FunctionsSkipCleanOutput>
    <GenerateDocumentationFile>True</GenerateDocumentationFile>
    <Nullable>enable</Nullable>
  </PropertyGroup>
  <ItemGroup>
    <PackageReference Include="Microsoft.ApplicationInsights.WorkerService" Version="2.22.0" />
    <PackageReference Include="Microsoft.AspNetCore.SignalR.Protocols.NewtonsoftJson" Version="8.0.7" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker" Version="1.22.0" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.ApplicationInsights" Version="1.2.0" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.DurableTask" Version="1.1.4" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.Http" Version="3.2.0" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.Http.AspNetCore" Version="1.3.2" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.Http.AspNetCore.Analyzers" Version="1.0.2" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.Rpc" Version="1.0.0" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.ServiceBus" Version="5.20.0" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.SignalRService" Version="1.14.0" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.Timer" Version="4.3.1" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Sdk" Version="1.17.4" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Sdk.Analyzers" Version="1.2.1" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Sdk.Generators" Version="1.3.2" />
    <PackageReference Include="SignalRSwaggerGen" Version="4.7.0" />
  </ItemGroup>
  <ItemGroup>
    <Using Include="System.Threading.ExecutionContext" Alias="ExcutionContext" />
  </ItemGroup>
</Project>

客户端应用程序:

<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>net8.0</TargetFramework>
    <ImplicitUsings>enable</ImplicitUsings>
    <Nullable>enable</Nullable>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="Microsoft.AspNetCore.SignalR.Client" Version="8.0.7" />
    <PackageReference Include="Microsoft.AspNetCore.SignalR.Protocols.NewtonsoftJson" Version="8.0.7" />
  </ItemGroup>
</Project>

链接到重现问题的存储库

https://github.com/Azure/azure-functions-dotnet-worker/tree/main/samples/Extensions/SignalR

c# .net signalr .net-8.0 signalr-hub
1个回答
1
投票

我做了一些调查,我从他们的官方存储库中重现了这个问题,在我看来,Microsoft.Azure.Functions.WorkerSystem.Threading.Channels包之间存在问题。返回对象是对流序列化传递的对象的分配,但它在某处消失了。不能说这是 System.Threading.Channels 中的调用问题还是 Microsoft.Azure.Functions.Worker 中的序列化问题。

© www.soinside.com 2019 - 2024. All rights reserved.