GitHub Actions and multi-project solutions
GitHub Actions can be a good choice for deploying an ASP.NET Core application to an Azure Web App Service if you have the code in a GitHub repository. You can even generate the GitHub Actions workflow directly from the Azure Portal. However, if your solution is not very simple, the generated workflow may not work correctly.
After you create the Azure Web App Service where you want to deploy your application, you can navigate to its Deployment Center page to create the initial GitHub Actions workflow. On the Settings tab, select GitHub as the Source, sign in with your account, and then select the Organization, Repository, and Branch with your code.
After optionally previewing the generated file, you can click Save to commit and push the file to your repository to trigger the deployment. A few minutes later, the workflow should complete and your application should be deployed to your Azure Web App Service.
However, if you have more than one project in your solution, it is likely that when you try to open the application in your browser, you will be greeted with a blank page instead of the application. If you check the files that were deployed, you will find that some of them should not have been deployed. In my case, all the files in my test project were deployed along with the application in the same server folder, which was the reason why the application could not be launched:
root@4f8e380d01af:~/site/wwwroot# ls *Tests* -l
-rwxrwxrwx 1 nobody nogroup 53989 Aug 6 14:08 WebApi.Tests.deps.json
-rwxrwxrwx 1 nobody nogroup 5632 Aug 6 14:08 WebApi.Tests.dll
-rwxrwxrwx 1 nobody nogroup 20500 Aug 6 14:08 WebApi.Tests.pdb
-rwxrwxrwx 1 nobody nogroup 351 Aug 6 14:08 WebApi.Tests.runtimeconfig.json
If you are familiar with .NET CLI, you should be able to spot the problem in the generated workflow file, even if you do not know much about GitHub Actions. The following step is responsible for publishing the application files to a local folder before uploading them to Azure:
- name: dotnet publish
run: dotnet publish -c Release -o ${{env.DOTNET_ROOT}}/myapp
Since no project is specified, the command publishes the files from all projects in the repository, which results in too many files being uploaded to the server. You can fix the problem by specifying the path to the project file of the application that you want to deploy:
- name: dotnet publish
run: dotnet publish ./WebApi/WebApi.csproj -c Release -o ${{env.DOTNET_ROOT}}/myapp
When you push the change to your repository, a new workflow run is automatically triggered. This time, the application should deploy correctly. It should open in the browser as expected. And when you check the files on the server, you should see only those that belong to the specified project:
root@de4bcb22d388:~/site/wwwroot# ls * -l
-rwxrwxrwx 1 nobody nogroup 173960 Aug 6 14:20 Microsoft.OpenApi.dll
-rwxrwxrwx 1 nobody nogroup 14848 Aug 6 14:20 Swashbuckle.AspNetCore.Swagger.dll
-rwxrwxrwx 1 nobody nogroup 90112 Aug 6 14:20 Swashbuckle.AspNetCore.SwaggerGen.dll
-rwxrwxrwx 1 nobody nogroup 3731456 Aug 6 14:20 Swashbuckle.AspNetCore.SwaggerUI.dll
-rwxrwxrwx 1 nobody nogroup 142840 Aug 6 14:20 WebApi
-rwxrwxrwx 1 nobody nogroup 4013 Aug 6 14:20 WebApi.deps.json
-rwxrwxrwx 1 nobody nogroup 9216 Aug 6 14:20 WebApi.dll
-rwxrwxrwx 1 nobody nogroup 20508 Aug 6 14:20 WebApi.pdb
-rwxrwxrwx 1 nobody nogroup 469 Aug 6 14:20 WebApi.runtimeconfig.json
-rwxrwxrwx 1 nobody nogroup 119 Aug 6 14:20 appsettings.Development.json
-rwxrwxrwx 1 nobody nogroup 142 Aug 6 14:20 appsettings.json
-rwxrwxrwx 1 nobody nogroup 482 Aug 6 14:21 web.config
You can check the code in my GitHub repository. The working workflow file is in the last commit, the broken one in the one before.
GitHub Actions are a great CI/CD solution for GitHub repositories. There are many integrations and templates to help you get started, including one in the Azure Portal for Azure Web App Services. That said, you may soon need to learn more about GitHub Actions to fix issues in the templates or customize them to your liking. Thanks to the excellent documentation, this should not be too difficult. If you use .NET, you can also read my article in DotNetCurry with instructions for some common scenarios.