Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Azure WebJob won't run locally in debugger

My Azure WebJob used to run in the VS2015 Debugger, but I found it gradually became very intermittent and now won't run at all. It works fine it I deploy it to Azure. The job is marked as RunOnStartUp.

public class Program
{
    static void Main()
    {
        var config = new JobHostConfiguration();
        config.UseTimers();
        var host = new JobHost(config);
        host.RunAndBlock();
    }
}

public class TestJob : BaseJob
{
    public static async Task StartupJob([TimerTrigger("05:00:00", RunOnStartup = true)] TimerInfo timerInfo, TextWriter log)
    {
        log.WriteLine("StartupJob");
        await Jobs.Test(some params);
        log.WriteLine("Sorted");
    }
}

What do I need to do to get it running in the Debugger?

like image 721
Rob Sedgwick Avatar asked Dec 05 '22 16:12

Rob Sedgwick


2 Answers

I'm guessing you use the same storage account for your job in Azure and when you debug it locally? If that's the case - the TimeTrigger runs as a singleton which means it needs to acquire a lock to be able to execute. If your webjob is already running in Azure your local version, which you're trying to debug, is not able to acquire the lock.

To avoid this just use different storage accounts for "live" Azure version and local local development.

I would also recommend to enable "development settings" - config.UseDevelopmentSettings(); - when you debug locally. If you enable it you'll see the messages "unable to acquire lock for function..." (or something similar).

like image 118
Rafal Zajac Avatar answered Jan 16 '23 08:01

Rafal Zajac


See Jason Haley's comment in this thread:

(total hack but should work) rename the function while debugging so the lock listener blob name will be different.

This hack worked for me. Maybe to make it less hacky, you could use the Disable-attribute to create a timer-triggered function that would only be enabled in your local environment:

  1. Create "MyFunction", which handles the logic. This is the one that will run in your Azure app. Note RunOnStartup=false as recommended by the docs.

     [FunctionName("MyFunction")]
     public async Task RunJob(
         [TimerTrigger("0 0 0 * * *", RunOnStartup = false)] TimerInfo timer)
     {
        //logic here
     }
    
  2. Create "MyFunction-Local" with the Disable attribute and a different method name. All this does is call the method above.

     [FunctionName("MyFunction-Local")]
     [Disable("Disable_MyFunction")]
     public async Task RunJobLocal(
         [TimerTrigger("0 0 0 * * *", RunOnStartup = true)] TimerInfo timer)
     {
        RunJob(timer);
     }
    
  3. In your local app configuration, set {"Disable_MyFunction" = false}, whereas for the app running in Azure, set this to true.

like image 33
unie Avatar answered Jan 16 '23 06:01

unie