Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Unit Test a Time Triggered Azure Function

I've got a time-triggered Azure Function which I want to test with XUnit and MOQ.

While I know I need to call the Run method of the class using an instance of the class say funTimeTriggeredObj where

funTimeTriggered funTimeTriggeredObj = new funTimeTriggered(queueSchedulerMock.Object, telemetryHelperMock.Object)

like

funTimeTriggeredObj.Run(param1, param2, loggerMock.Object) 

where

private Mock<ILogger> loggerMock = new Mock<ILogger>() 

I'm not sure how should I mock the param1 & param2 which are TimerInfo and ExecutionContext objects respectively.

The reason why I'm asking is because neither 'TimerInfo' nor 'ExecutionContext' implements any interface which can be mocked.

Below is my actual function implementation. Any help whatsoever would be highly appreciated.

using System;
using System.Threading.Tasks;
using Microsoft.Azure.WebJobs;
using Microsoft.Extensions.Logging;

public  class funTimeTriggered
{
    private  string  _invocationID;
    private readonly IQueueScheduler _queueScheduler;
    private readonly ITelemetryHelper _telemetryHelper;

    public funTimeTriggered(IQueueScheduler queueScheduler, ITelemetryHelper telemetryHelper)
    {
        _queueScheduler = queueScheduler;
        _telemetryHelper = telemetryHelper;
    }

    [FunctionName("funTimeTriggered")]
    public  async Task Run([TimerTrigger("0/10 * * * * *")]TimerInfo myTimer, ExecutionContext context, ILogger log)
    {
        log.LogInformation($"C# Timer trigger function executed at: {DateTime.Now}");
        try
        {
            _invocationID = context.InvocationId.ToString();
            await _queueScheduler.SendEventsToServiceBusAndDeleteFromSQS();
        }
        catch (Exception ex)
        {
            log.LogError(ex.Message);
            _telemetryHelper.LogException(ex);
            throw ex;
        }
    }
}
like image 292
The Inquisitive Coder Avatar asked Apr 01 '20 08:04

The Inquisitive Coder


People also ask

Can you unit test Azure functions?

When executing your Azure Functions, the functions runtime will run your function code with a concrete implementation of these interfaces. For unit testing, you can pass in a mocked version of these interfaces to test your business logic.

How do I create a timer trigger in Azure function?

Create a timer triggered functionIn your function app, select Functions, and then select + Create. Select the Timer trigger template. Configure the new trigger with the settings as specified in the table below the image, and then select Create. Defines the name of your timer triggered function.

Can a timed Azure function run multiple instances at the same time?

If a function app scales out to multiple instances, only a single instance of a timer-triggered function is run across all instances. It will not trigger again if there is an outstanding invocation is still running.


1 Answers

If there are no undesired effects of using actual instance of those classes and you can actually initialize them then create actual instance and pass them to the function under test.

They do not have to be interfaces or mocked if using the actual instance(s) has no unwanted effects

//Arrange

//...omitted for brevity

var param1 = new TimerInfo(...); 
var param2 = = new ExecutionContext {
    InvocationId = Guid.NewGuid()
};

//Act
await funTimeTriggeredObj.Run(param1, param2, loggerMock.Object);

//Assert
//...assert expected behavior

And since in this test case the timer is not even used by the function, it can be ignored altogether

//Arrange

//...omitted for brevity

var param1 = default(TimerInfo); //null
var param2 = = new ExecutionContext {
    InvocationId = Guid.NewGuid()
};

//Act
await funTimeTriggeredObj.Run(param1, param2, loggerMock.Object);

//Assert
//...assert expected behavior
like image 165
Nkosi Avatar answered Oct 04 '22 02:10

Nkosi