DEV Community

Kenichiro Nakamura
Kenichiro Nakamura

Posted on

Azure Function and .NET 5: How to retry with Queue Trigger

Any program may fail at some point, and we need to prepare for it. I will explain how we can retry Function App with Queue trigger.

Poison Queue

By default, the function app retries five times before give-up processing the queue item. Then, it sends the item to Poison queue so that developer can take a look later.

There are many reasons why it failed to process it, but most of the time, the item itself has issue, such as unexpected format of data.

Let's check the behavior.

Create Storage Queue

I use local storage emulator this time.

1. Make sure to run Azure Storage Emulator, and open Storage Explorer to connect to local storage queue.

image

2. Add new queue "testqueue".

image

Create Queue Trigger function

1. Create new folder, and new function in it.

mkdir queueretryfunc
cd queueretryfunc
func init --workder-runtime dotnetIsolated
func new -n queueretryfunc
Enter fullscreen mode Exit fullscreen mode

2. Select QueueTrigger.

image

3. Open with Visual Studio Code.

code .
Enter fullscreen mode Exit fullscreen mode

4. Open queuetryfunc.cs file and update QueueTrigger properties.

public static void Run([QueueTrigger("testqueue", Connection = "QueueConnectionString")] string myQueueItem,
            FunctionContext context)
Enter fullscreen mode Exit fullscreen mode

5. Open local.settings.json and add QueueConnectionString variable. Enter the appropriate value.

{
    "IsEncrypted": false,
    "Values": {
        "AzureWebJobsStorage": "UseDevelopmentStorage=true",
        "FUNCTIONS_WORKER_RUNTIME": "dotnet-isolated",
        "QueueConnectionString":"[your connection string]"
    }
}
Enter fullscreen mode Exit fullscreen mode

6. Back to queuetryfunc.cs and update the run method to simply return Exception.

using System;
using Microsoft.Azure.Functions.Worker;
using Microsoft.Extensions.Logging;

namespace queueretryfunc
{
    public static class queueretryfunc
    {
        [Function("queueretryfunc")]
        public static void Run([QueueTrigger("testqueue", Connection = "QueueConnectionString")] string myQueueItem,
            FunctionContext context)
        {
           throw new Exception();
        }
    }
}
Enter fullscreen mode Exit fullscreen mode

Test it!

1. Start function by func start.

func start
Enter fullscreen mode Exit fullscreen mode

image

2. Create new queue item in storage.

image

3. We can see the exception five times in the log. It indicates that the item was moved to poison queue.

image

4. Confirm that there is new queue and the created item in it.

image

Change time out and retry count

As we saw, the function immediately process the item five times, without any break, which may not be ideal situation in real scenario.

Let's change some settings to control the behavior.

Update host.json

To control the queue trigger behavior, we can update host.json.

1. Open host.json and update as below. This indicates we want to wait five seconds before next retry, and we only retry three times before sending the item to poison queue.

{
    "version": "2.0",
    "logging": {
        "applicationInsights": {
            "samplingSettings": {
                "isEnabled": true,
                "excludedTypes": "Request"
            }
        }
    },
    "extensions": {
        "queues": {
            "visibilityTimeout": "00:00:05",
            "maxDequeueCount": 3
        }
    }
}
Enter fullscreen mode Exit fullscreen mode

2. Run the function again, and add new item in the queue.

3. Then, check the log to see there is more than five seconds intervals between each Exception, and it retries three times only.

image
image
image
image

Summary

It's quite easy to control the behavior only if we know where to update. See here for complete list and detail explanation of the settings.

Top comments (0)