While publishing a web application you get a puzzling error that reads like the following in the output window:
1>C:\WINDOWS\Microsoft.NET\Framework\v4.0.30319\aspnet_compiler.exe -v \ -p C:\Dev\WebApp\obj\Release\AspnetCompileMerge\Source C:\Dev\WebApp\obj\Release\AspnetCompileMerge\TempBuildDir
1>ASPNETCOMPILER(0,0): Error ASPCONFIG: Could not load file or assembly ‘SomeAssembly, Version=220.127.116.11, Culture=neutral, PublicKeyToken=null’ or one of its dependencies. Access is denied.
When you get this error the first thing you think is that you have a broken reference or there is a permissions issue. That may very well be the problem so I strongly suggest looking around on google before continuing with this solution because I think I hit a very strange edge case that isn’t likely going to be the problem for most people.
Here is a list of common issues that people can run into when dealing with a problem like this.
- The User group from windows doesn’t have the necessary modify permissions on a particular folder
- You have a bad reference
- You have mismatched NuGet assembly versions
- You have mismatched assembly versions in general
- You have mismatched framework target versions across projects (A .Net 4.0 project is referencing a .Net 4.61 project – this is not allowed)
- You have mixed architecture targets across projects (x86 vs x64 vs Any CPU)
- A specific dll in your bin folder is marked as Read Only and won’t be deleted causing the build to fail
In my case my publish profile wasn’t matching the solution configuration’s name. This was causing me to get the error stated above. I am going to attempt to explain this as well as I can because the following is an obfuscated view of what I was actually working on. I cannot disclose actual names, so I had to change a lot of this content – however the point here is to see where there are some oddities that were being generated:
1>—— Build started: Project: WebApp, Configuration: Release Any CPU ——
1> WebApp -> C:\Dev\Web\bin\WebApp.dll
2>—— Publish started: Project: WebApp, Configuration: Release Any CPU ——
2>Connecting to C:\Apps\PublishTest…
2>Transformed Web.config using C:\Dev\Web\Web.Release.config into obj\Release\TransformWebConfig\transformed\Web.config.
2>Transformed obj\Release\TransformWebConfig\transformed\Web.config using C:\Dev\Web\\Web.UAT .config into obj\Release\ProfileTransformWebConfig\transformed\Web.config.
2>Copying all files to temporary location below for package/publish:
2>C:\WINDOWS\Microsoft.NET\Framework\v4.0.30319\aspnet_compiler.exe -v \ -p C:\Dev\Web\obj\Release\AspnetCompileMerge\Source C:\Dev\Web\obj\Release\AspnetCompileMerge\TempBuildDir
2>ASPNETCOMPILER(0,0): Error ASPCONFIG: Could not load file or assembly ‘AAS.FacilityScheduler.Business, Version=18.104.22.168, Culture=neutral, PublicKeyToken=null’ or one of its dependencies. Access is denied.
========== Build: 1 succeeded, 0 failed, 7 up-to-date, 0 skipped ==========
========== Publish: 0 succeeded, 1 failed, 0 skipped ==========
If you direct your attention to the highlighted portion you can see one problem here: “There is a double slash”
I don’t understand how these two things contribute to the error, but they aren’t right either. Not to mention that there is a double web.config transformation going on here. So the whole thing is kind of screwy to begin with. None of that should be happening and apparently it is all due to the fact that I was targeting the wrong solution profile (whether it is wrong or not is truly debatable).
The way I have my publish profiles setup is that there is a profile per client and per environment. For argument’s sake let’s say I have a client named “Bob”. Then I would have:
- Prod Bob.pubxml – production publish profile
- Web.Prod Bob.config – production transformation file for the web.config
- Prod Bob – production build configuration
- UAT Bob.pubxml – production publish profile
- Web.UAT Bob.config – production transformation file for the web.config
- UAT Bob – UAT build configuration
In addition to the above configurations everyone has the following build configurations by default:
- Debug (Any CPU)
- Release (Any CPU)
By default there isn’t a transformation file for the web.config, but you can create one per build configuration. In my case I ran into the following problem:
<!-- This is just an excerpt of my UAT Bob.pubxml --> <?xml version="1.0" encoding="utf-8"?> <Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> <PropertyGroup> <WebPublishMethod>MSDeploy</WebPublishMethod> <ADUsesOwinOrOpenIdConnect>False</ADUsesOwinOrOpenIdConnect> <LastUsedBuildConfiguration>Release</LastUsedBuildConfiguration> <LastUsedPlatform>Any CPU</LastUsedPlatform> ... </PropertyGroup> </Project>
The problem is very easy to miss because I wasted about 4 hours trying to figure this out. However the problem here is that the tag that says “LastUsedBuildConfiguration” was set to “Release” which doesn’t match for this profile. It should read “UAT Bob” so that it uses the “UAT Bob” build configuration. The moment I changed this, the build started working and I wasn’t getting errors anymore.
Wow, how annoying… I don’t feel like it should work this way, but I am sure it is because I have transformation files involved in this process that it isn’t working. I bet this would have worked just fine if I wasn’t using transformation files.