问题
I'm working with a Service Bus queue triggered function.
When we manually (and crucially immediately) DeadLetter the BrokeredMessage, it does indeed go to the dead letter queue.
However, the runtime reports the following error:
The lock supplied is invalid. Either the lock expired, or the message has already been removed from the queue
Example function:
[FunctionName("MySbFunction")]
public static async Task Run(
[ServiceBusTrigger("topic-name", "subscription-name", AccessRights.Manage, Connection = "xxx")] BrokeredMessage msg,
ILogger log)
{
await msg.DeadLetterAsync();
}
The same happens if we .CompleteAsync();
the message instead - the message is completed, however the runtime throws an error.
I understand the normal way of dead-lettering the message would be to throw an exception during the execution, causing the function to fail, retrying the message.
My issue with this approach is sometimes the message is unrecoverable - trying it x times won't yield another result.
The reason I'd like to .CompleteAsync();
a message is for retry:
I could:
.Clone();
the originalBrokeredMessage
- Set it's
ScheduledEnqueueTimeUtc
property. .CompleteAsync();
the original message- put the cloned message back on the queue (via output binding)
This technically works, but the runtime still reports the above mentioned error, when completing the message outside of it's expected flow.
回答1:
The problem is that the runtime manages Service Bus message completion itself, calling Complete
after successful invocation or Abandon
in case of exception.
There was a feature request to opt out of such behavior and manage the completion manually inside the Function. The fix is implemented, I'm not sure if it's in the current runtime or not, but docs weren't updated yet.
Follow the issue above to know the status.
来源:https://stackoverflow.com/questions/51881103/calling-complete-or-deadletter-on-brokeredmessage-with-azure-functions-service