Azure函数-ServiceBusTrigger-异常绑定消息 [英] Azure Function - ServiceBusTrigger - Exception Binding Message

查看:75
本文介绍了Azure函数-ServiceBusTrigger-异常绑定消息的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个已订阅Azure Service Bus队列的Azure函数-但是,在该函数能够触发异常之前,运行时会在它到达我的任何代码之前引发异常。

 执行函数:< functionName>时发生异常。 Microsoft.Azure.WebJobs.Host:异常绑定参数 message。 System.Private.CoreLib:无法将索引60处的字节[9A]从指定的代码页转换为Unicode。 

在这种情况下,我无法控制传入消息(它实际上是从Azure DevOps发送的订阅),因此我需要使该函数更加灵活,以免引发该异常。



我的函数如下:

  [FunctionName( FunctionName)] 
public static async Task Run(
[ServiceBusTrigger( Queue,Connection = ConnectionString)] byte []消息)

我看到了其他问题,建议不再使用 Message BrokeredMessage 对象,并使用 byte [] (并编写您自己的编码来解决该问题),但这对我没有用。看来运行时仍在尝试并无法对消息执行某些操作,直到消息到达我的功能。



如何避免此问题?






由于我尚未找到如何解决此问题的方法,因此我将保留此问题-但是,现在我已经看到了如何解决该问题的方法实例。我一直在努力处理的消息是



Tl;博士->如果您遇到此问题,请确保选中以上选项





相关代码(Microsoft.Azure.WebJobs.ServiceBus.Triggers.UserTypeArgumentBindingProvider)

 私有静态TInput GetBody(消息消息,ValueBindingContext上下文)
{
if(message.ContentType == ContentTypes.ApplicationJson)//正在查看消息类型
{
字符串内容;

的内容= StrictEncodings.Utf8.GetString(message.Body);

试试
{
return JsonConvert.DeserializeObject< TInput>(contents,Constants.JsonSerializerSettings);
}
catch(JsonException e)
{
//容易使队列有效负载无法正确反序列化。因此,给出一个有用的错误。
字符串msg = string.Format(
@将参数绑定到复杂对象(例如'{0}')使用Json.NET序列化。
1.将参数类型绑定为'string '而不是'{0}'来获取原始值并避免JSON反序列化或
2.将队列有效负载更改为有效json。JSON解析器失败:{1}
,typeof( TInput).Name,e.Message);
抛出新的InvalidOperationException(msg);
}
}
else
{
返回消息。GetBody< TInput>();
}
}
}


I have an Azure Function that is subscribed to an Azure Service Bus Queue - however before the function is able to trigger an exception is thrown by the run time before it reaches any of my code.

Exception while executing function: <functionName>. Microsoft.Azure.WebJobs.Host: Exception binding parameter 'message'. System.Private.CoreLib: Unable to translate bytes [9A] at index 60 from specified code page to Unicode.

In this instance I am not in control of the incoming message (it's actually being sent from an Azure DevOps Subscription) so I need to be able to make the function more flexible so that this exception isn't thrown.

My function looks like this:

[FunctionName("FunctionName")]
public static async Task Run(
    [ServiceBusTrigger("Queue", Connection = "ConnectionString")] byte[] message)

I have seen other question that suggest moving away from using a Message or BrokeredMessage object and to use byte[] instead (and write your own encoding to deal with the issue) but this hasn't worked for me. It appears that the runtime is still trying and failing to do something to the message before it reaches my function.

How can I avoid this issue?


I will leave this question open because I haven't yet found how to solve this problem - however I have now seen how to fix it in my instance. The messages that I've been struggling to handle are messages that are delivered by AzureDevOps ServiceHooks. If I go into the settings (when creating or editing) the service hooks found here -> https://.visualstudio.com//_settings/serviceHooks

There is a tick box that I missed. In order for an Azure Function to be able to process the message this tick box needs to selected. I.e. you want to send as a non-serialised string. This must be because whatever client sits in-between my function and the queue can't handle a .Net serialised message.

Tl;Dr -> If you have this issue make sure this option above is selected

GitHub Issue Tracking the problem

解决方案

The issue is that the Functions library is looking at the message type instead of the type specified in the function when deciding whether or not to decode it. Since Devops is sending the message as type application/json, the library is trying, and failing to decode it using UTF8.

For now, choosing "send as non-serialized string" is a valid workaround. The issue can be tracked on Github: https://github.com/Azure/azure-webjobs-sdk/issues/2234

Relevant code (Microsoft.Azure.WebJobs.ServiceBus.Triggers.UserTypeArgumentBindingProvider)

 private static TInput GetBody(Message message, ValueBindingContext context)
        {
            if (message.ContentType == ContentTypes.ApplicationJson) //This is looking at the message type
            {
                string contents;

                contents = StrictEncodings.Utf8.GetString(message.Body);

                try
                {
                    return JsonConvert.DeserializeObject<TInput>(contents, Constants.JsonSerializerSettings);
                }
                catch (JsonException e)
                {
                    // Easy to have the queue payload not deserialize properly. So give a useful error. 
                    string msg = string.Format(
    @"Binding parameters to complex objects (such as '{0}') uses Json.NET serialization. 
    1. Bind the parameter type as 'string' instead of '{0}' to get the raw values and avoid JSON deserialization, or
    2. Change the queue payload to be valid json. The JSON parser failed: {1}
    ", typeof(TInput).Name, e.Message);
                    throw new InvalidOperationException(msg);
                }
            }
            else
            {
                return message.GetBody<TInput>();
            }
        }
    }

这篇关于Azure函数-ServiceBusTrigger-异常绑定消息的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆