Search code examples
c#.net-8.0dotnet-cliazure-functions-core-toolsazure-functions-isolated

"No job functions found" warning when upgrading Microsoft.Azure.Functions.Worker.Sdk to 1.16.1 or above


Background

I am trying to migrate my HTTP-triggered Azure Functions Apps to isolated process. For myself to understand how an isolated-process Functions app work, I started from the template provided by the Azure Functions Core Tools (version 4.0.5348 - the latest NixOS provides at the time of writing) following official Quick-Start Guide.

The template works without upgrading any of the libraries that come with it. One can visit the local address http://localhost:7071/api/HttpExample and see the HTTP response Welcome to Azure Functions!.

However, if after I upgraded the libraries to the latest version, the HTTP-triggered API stopped working and gave me the following warning message.

No job functions found. Try making your job classes and methods public. If you're using binding extensions (e.g. Azure Storage, ServiceBus, Timers, etc.) make sure you've called the registration method for the extension(s) in your startup code (e.g. builder.AddAzureStorage(), builder.AddServiceBus(), builder.AddTimers(), etc.).

The Question

How do I modify the codebase from the templates to fix this problem and let the Azure Functions app run under the latest Microsoft.Azure.Functions.Worker.Sdk?

The cause

The library versions come with the framework, at the time of writing, are

   [net8.0]:
   Top-level Package                                       Requested   Resolved
   > Microsoft.Azure.Functions.Worker                      1.19.0      1.19.0
   > Microsoft.Azure.Functions.Worker.Extensions.Http      3.0.13      3.0.13
   > Microsoft.Azure.Functions.Worker.Sdk                  1.14.0      1.14.0

The latest library versions, at the time of writing, are

   [net8.0]:
   Top-level Package                                       Requested   Resolved
   > Microsoft.Azure.Functions.Worker                      1.21.0      1.21.0
   > Microsoft.Azure.Functions.Worker.Extensions.Http      3.1.0       3.1.0
   > Microsoft.Azure.Functions.Worker.Sdk                  1.17.2      1.17.2

After a few trial-and-errors, I found out the problem was upgrading Microsoft.Azure.Functions.Worker.Sdk and its latest working version with the template is 1.15.1 - upgrading it to 1.16.0, the next version, will reproduce the error.

Possible roots of the problem - my suspicions

  1. A bug in Microsoft.Azure.Functions.Worker.Sdk since 1.16.0
  2. Azure Functions Core Tools outdated
  3. Project/Function template outdated - we need something

Summary of steps to reproduce the problem

  1. Install the Azure Functions Core Tools version 4.0.5348 on a Linux system.
  2. Create project from template
    • func init LocalFunctionProj --worker-runtime dotnet-isolated --target-framework net8.0
  3. Create function from template
    • cd LocalFunctionProj
    • func new --name HttpExample --template "HTTP trigger" --authlevel "anonymous"
  4. Upgrade Microsoft.Azure.Functions.Worker.Sdk
    • dotnet add package Microsoft.Azure.Functions.Worker.Sdk
  5. Run the Functions app locally
    • func start --debug --verbose

Codebase

The codebase is listed in this GitHub repository.

Similar questions

This question is the closest, but it is about upgrading from existing project but not about creating a brand new one.


Solution

  • Isolated Function does work while using the latest libraries.

    • I also have created the function using below commands-
     - func init LocalFunctionProj --worker-runtime dotnet-isolated --target-framework net8.0
     - cd LocalFunctionProj
     - func new --name HttpExample --template "HTTP trigger" --authlevel "anonymous"
    
    • It creates all the function related files which has below code in it.

    HttpExample.cs-

    using System.Net;
    using Microsoft.Azure.Functions.Worker;
    using Microsoft.Azure.Functions.Worker.Http;
    using Microsoft.Extensions.Logging;
    
    namespace LocalFunctionProj
    {
        public class HttpExample
        {
            private readonly ILogger _logger;
    
            public HttpExample(ILoggerFactory loggerFactory)
            {
                _logger = loggerFactory.CreateLogger<HttpExample>();
            }
    
            [Function("HttpExample")]
            public HttpResponseData Run([HttpTrigger(AuthorizationLevel.Anonymous, "get", "post")] HttpRequestData req)
            {
                _logger.LogInformation("C# HTTP trigger function processed a request.");
    
                var response = req.CreateResponse(HttpStatusCode.OK);
                response.Headers.Add("Content-Type", "text/plain; charset=utf-8");
    
                response.WriteString("Welcome to Azure Functions!");
    
                return response;
            }
        }
    }
    

    local.settings.json-

    {
        "IsEncrypted": false,
        "Values": {
            "AzureWebJobsStorage": "UseDevelopmentStorage=true",
            "FUNCTIONS_WORKER_RUNTIME": "dotnet-isolated"
        }
    }
    

    program.cs-

    using Microsoft.Extensions.Hosting;
    
    var host = new HostBuilder()
        .ConfigureFunctionsWorkerDefaults()
        .Build();
    
    host.Run();
    

    host.json-

    {
        "version": "2.0",
        "logging": {
            "applicationInsights": {
                "samplingSettings": {
                    "isEnabled": true,
                    "excludedTypes": "Request"
                },
                "enableLiveMetricsFilters": true
            }
        }
    }
    
    • After updating the packages .csproj look like below-
    <Project Sdk="Microsoft.NET.Sdk">
      <PropertyGroup>
        <TargetFramework>net8.0</TargetFramework>
        <AzureFunctionsVersion>v4</AzureFunctionsVersion>
        <OutputType>Exe</OutputType>
        <ImplicitUsings>enable</ImplicitUsings>
        <Nullable>enable</Nullable>
      </PropertyGroup>
      <ItemGroup>
        <PackageReference Include="Microsoft.Azure.Functions.Worker" Version="1.21.0" />
        <PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.Http" Version="3.1.0" />
        <PackageReference Include="Microsoft.Azure.Functions.Worker.Sdk" Version="1.17.3-preview1" />
      </ItemGroup>
      <ItemGroup>
        <None Update="host.json">
          <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
        </None>
        <None Update="local.settings.json">
          <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
          <CopyToPublishDirectory>Never</CopyToPublishDirectory>
        </None>
      </ItemGroup>
      <ItemGroup>
        <Using Include="System.Threading.ExecutionContext" Alias="ExecutionContext" />
      </ItemGroup>
    </Project>
    
    • Now, when I executed the function, I am getting expected response.

    enter image description here

    • If you are still not getting output, I would suggest you to try creating the function from the scratch.