Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

OOB Library's AssemblyVersion is inconsistent between ref and src assemblies in servicing #63467

Closed
eerhardt opened this issue Jan 6, 2022 · 2 comments · Fixed by #78703
Closed

Comments

@eerhardt
Copy link
Member

eerhardt commented Jan 6, 2022

When servicing a library that targets .NET Framework, we are bumping up the AssemblyVersion on the .NET Framework assemblies:

<_AssemblyInTargetingPack Condition="('$(IsNETCoreAppSrc)' == 'true' or '$(_IsAspNetCoreApp)' == 'true' or '$(_IsWindowsDesktopApp)' == 'true') and '$(TargetFrameworkIdentifier)' != '.NETFramework'">true</_AssemblyInTargetingPack>
<!-- Assembly version do not get updated in non-netfx ref pack assemblies. -->
<AssemblyVersion Condition="'$(_AssemblyInTargetingPack)' != 'true'">$(MajorVersion).$(MinorVersion).0.$(ServicingVersion)</AssemblyVersion>

However, this is only applying to the src project, because this logic is contained in packaging.targets which is only imported for the src project. For the ref project the AssemblyVersion is staying 6.0.0.0, since this logic doesn't run and because the ServicingVersion is only defined in the src project.

I hit this problem because we have a test which was failing trying to load a serviced assembly:

Unhandled Exception: System.IO.FileLoadException: Could not load file or assembly 'Microsoft.Extensions.Hosting, Version=6.0.0.0, Culture=neutral, PublicKeyToken=adb9793829ddae60' or one of its dependencies. The located assembly's manifest definition does not match the assembly reference. (Exception from HRESULT: 0x80131040)

The reason this happened is because the ref assembly for Microsoft.Extensions.Hosting was being passed to the test, so the test was getting a reference to Version=6.0.0.0. But the src assembly is used at runtime, which is version 6.0.0.1. No assembly binding redirect is getting generated for this reference because the test is the "top" of the dependency chain and no one else is referencing a lower version of Microsoft.Extensions.Hosting. So no redirect is getting generated.

This can also cause issues when a serviced library has a ProjectToProject reference to another serviced library. Microsoft.Extensions.Hosting references Microsoft.Extensions.Configuration.UserSecrets. The Hosting package version of 6.0.1 will reference the UserSecrets package version 6.0.1. UserSecrets v6.0.1 will contain the 6.0.0.1 netfx assembly. However Hosting v6.0.1's netfx assembly will have a binary reference to 6.0.0.0 because that's what the ref assembly for UserSecrets is during our build.

In talking with @ericstj, we think the correct thing to do here is to ensure both the ref and src assemblies get the same AssemblyVersion during servicing.

@safern

@dotnet-issue-labeler dotnet-issue-labeler bot added area-Infrastructure-libraries untriaged New issue has not been triaged by the area owner labels Jan 6, 2022
@ghost
Copy link

ghost commented Jan 6, 2022

Tagging subscribers to this area: @dotnet/area-infrastructure-libraries
See info in area-owners.md if you want to be subscribed.

Issue Details

When servicing a library that targets .NET Framework, we are bumping up the AssemblyVersion on the .NET Framework assemblies:

<_AssemblyInTargetingPack Condition="('$(IsNETCoreAppSrc)' == 'true' or '$(_IsAspNetCoreApp)' == 'true' or '$(_IsWindowsDesktopApp)' == 'true') and '$(TargetFrameworkIdentifier)' != '.NETFramework'">true</_AssemblyInTargetingPack>
<!-- Assembly version do not get updated in non-netfx ref pack assemblies. -->
<AssemblyVersion Condition="'$(_AssemblyInTargetingPack)' != 'true'">$(MajorVersion).$(MinorVersion).0.$(ServicingVersion)</AssemblyVersion>

However, this is only applying to the src project, because this logic is contained in packaging.targets which is only imported for the src project. For the ref project the AssemblyVersion is staying 6.0.0.0, since this logic doesn't run and because the ServicingVersion is only defined in the src project.

I hit this problem because we have a test which was failing trying to load a serviced assembly:

Unhandled Exception: System.IO.FileLoadException: Could not load file or assembly 'Microsoft.Extensions.Hosting, Version=6.0.0.0, Culture=neutral, PublicKeyToken=adb9793829ddae60' or one of its dependencies. The located assembly's manifest definition does not match the assembly reference. (Exception from HRESULT: 0x80131040)

The reason this happened is because the ref assembly for Microsoft.Extensions.Hosting was being passed to the test, so the test was getting a reference to Version=6.0.0.0. But the src assembly is used at runtime, which is version 6.0.0.1. No assembly binding redirect is getting generated for this reference because the test is the "top" of the dependency chain and no one else is referencing a lower version of Microsoft.Extensions.Hosting. So no redirect is getting generated.

This can also cause issues when a serviced library has a ProjectToProject reference to another serviced library. Microsoft.Extensions.Hosting references Microsoft.Extensions.Configuration.UserSecrets. The Hosting package version of 6.0.1 will reference the UserSecrets package version 6.0.1. UserSecrets v6.0.1 will contain the 6.0.0.1 netfx assembly. However Hosting v6.0.1's netfx assembly will have a binary reference to 6.0.0.0 because that's what the ref assembly for UserSecrets is during our build.

In talking with @ericstj, we think the correct thing to do here is to ensure both the ref and src assemblies get the same AssemblyVersion during servicing.

@safern

Author: eerhardt
Assignees: -
Labels:

area-Infrastructure-libraries, untriaged

Milestone: -

@safern safern removed the untriaged New issue has not been triaged by the area owner label Jan 7, 2022
@safern safern added this to the 6.0.x milestone Jan 7, 2022
@ViktorHofer
Copy link
Member

ViktorHofer commented May 6, 2022

@ericstj do you know if anyone started working on this? Based on

<PropertyGroup Condition="'$(PreReleaseVersionLabel)' == 'servicing'">
<!-- If no servicing version is set we need to default to 0 in order for dependency versions to
be calculated propertly, if we don't set it to 0, we would get the dependency version using the
product Patch Version -->
<ServicingVersion Condition="'$(ServicingVersion)' == ''">0</ServicingVersion>
<!-- Always update the package version in servicing. -->
<Version>$(MajorVersion).$(MinorVersion).$(ServicingVersion)</Version>
<Version Condition="'$(VersionSuffix)' != ''">$(Version)-$(VersionSuffix)</Version>
<_IsWindowsDesktopApp Condition="$(WindowsDesktopCoreAppLibrary.Contains('$(AssemblyName);'))">true</_IsWindowsDesktopApp>
<_IsAspNetCoreApp Condition="$(AspNetCoreAppLibrary.Contains('$(AssemblyName);'))">true</_IsAspNetCoreApp>
<_AssemblyInTargetingPack Condition="('$(IsNETCoreAppSrc)' == 'true' or '$(IsNetCoreAppRef)' == 'true' or '$(_IsAspNetCoreApp)' == 'true' or '$(_IsWindowsDesktopApp)' == 'true') and '$(TargetFrameworkIdentifier)' != '.NETFramework'">true</_AssemblyInTargetingPack>
<!-- Assembly version do not get updated in non-netfx ref pack assemblies. -->
<AssemblyVersion Condition="'$(_AssemblyInTargetingPack)' != 'true'">$(MajorVersion).$(MinorVersion).0.$(ServicingVersion)</AssemblyVersion>
</PropertyGroup>
, it looks like the AssemblyVersion is still only set for the source project (because packaging.targets isn't imported in a ref project because it usually isn't packable). Do we still need this for servicing 6.0?

Alternatively we could fix this by removing the out-of-band reference projects as they aren't shipping anymore anyways since NET6 which would have the added benefit of making the build graph smaller which has a positive impact on build times, solution file size, maintenance costs of the ref, etc.

@ghost ghost added the in-pr There is an active PR which will close this issue when it is merged label Nov 22, 2022
@ghost ghost removed the in-pr There is an active PR which will close this issue when it is merged label Nov 22, 2022
@ghost ghost locked as resolved and limited conversation to collaborators Dec 22, 2022
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants