-
Notifications
You must be signed in to change notification settings - Fork 4.6k
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
System.Net.Http v4.2.0.0 being copied/loaded from MSBuild tooling #24382
Comments
My apologies, it seems the author of the previous comment I referenced did in fact open an issue here: https://github.com/dotnet/corefx/issues/23306 However, I'm trying to read that chain and understand the final outcome. It isn't clear to me what I'm doing wrong in my fairly basic scenario. It seems very confusing/wrong that I'm getting System.Net.Http v4.2.0.0 introduced into my build. At the very least, I guess I'm still unclear on the simplest path to resolve the issue. |
Doing that kind of binding redirect is the correct workaround to this problem. However, you should just bind back to the 4.0.0..0 version. Doing so will ensure you use the GAC'd version of System.Net.Http.dll from the .NET Framework and not use the System.Net.Http.dll binary from the NuGet package. I.e. <runtime>
<assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
<dependentAssembly>
<assemblyIdentity name="System.Net.Http" publicKeyToken="b03f5f7f11d50a3a" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-4.2.0.0" newVersion="4.0.0.0" />
</dependentAssembly>
</assemblyBinding>
</runtime> Although, reading your repro steps above, I don't understand why you would explicitly do these steps:
If you're building a .NET Framework 4.6.x app, you should just use standard references to System.Net.Http and not bring in any Nuget package for System.Net.Http. |
cc: @karelz @terrajobst - more packaging issues related to bindings. |
Thanks for the feedback! This may be the key concept I'm struggling with:
Honestly, when targeting .NET Framework, I'm often confused why I usually end up with nuget package references targeting System.* (something I know should be in the framework). But this happens to me all the time. When building an app targeting 4.6.X a reference to the GAC'd version of System.Net.Http is included by default and I wouldn't think I need to add the nuget package for System.Net.Http. However, the real scenario where I encountered this problem results from my top level app ultimately referencing some other nuget packages that have a dependency on System.Net.Http from nuget (IdentityModel was the particular package introducing it for me). Thus, my project will end up with nuget package references to System.Net.Http regardless. In my simple repro, I agree it wouldn't be something I'd need to do. In my experience, apps targeting .NET 4.6.x often end up with a nuget package dependency on System.Net.Http because of other packages. Is this a mistake/flaw in 3rd party packages for them to have a dependency on System.Net.Http package for .net 4.6.x? Or is there a valid reason why they need that? It is a generalization, but it feel like I run into System.Net.Http package issues a LOT. I think what you are saying is that the general rule of thumb should be: If your top level app is targeting .NET 4.6.x you will want to redirect any references to System.Net.Http (even higher versions!!) to 4.0.0.0 since that is what should be in the framework GAC. Am I understanding that correctly? Note that my project has true so as a developer I'm hoping/praying to never have to make manual decisions about my binding redirects (because most of us find them very annoying to have to try and think about and manage). What is odd, is that if I don't have any redirects in my app.config, none are generated at compile time. However, if I add the redirect you mentioned (to v4.0.0.0) the config file generated at compile time actually is changed to redirect to 4.1.1.2. That doesn't really matter, I'm just noting that all this feels very confusing and not very intuitive to simple minded folk like me. I very much appreciate your feedback and guidance! |
Also, Can you confirm that getting v4.2.0.0 referenced from C:\Program Files (x86)\Microsoft Visual Studio\2017\Enterprise\MSBuild\Microsoft\Microsoft.NET.Build.Extensions\net461\lib\System.Net.Http.dll would be expected/desirable? |
So, it's actually even more complicated unfortunately. In the old days, there were just references to .NET Framework assemblies. Then came NuGet packages which added some complexity. Recently with NETStandard20, developers can build class library that target NETStandard20 and use those on .NET Framework and/or .NET Core. System.Net.Http is available in a NuGet package because we made a decision early in .NET Core development to add new APIs to System.Net.Http. But because those APIs at the time were not in .NET Framework 4.6.x, we created a new "out-of-band" (OOB) package that contained the revised implementation and thus could carry the updated API for developers that wanted it. We later discovered that creating new System.Net.Http binaries outside of the .NET Framework had issues such as what you are discovering. So, we have revised that approach. We added those new APIs directly to .NET Framework 4.7.1 as part of the NETStandard20 reconcillation effort. And we have been improving tooling to help reconcile some of these version conflicts.
Yes, most problems that developers are seeing with System.Net.Http assembly version mismatches is that they aren't explicitly pulling in the NuGet System.Net.Http but rather implicitly thru other package references. Getting this problem smoothed out for developers relies on getting the binding redirects fixed up. Visual Studio 2017 has made some additional tooling changes in the latest updates (15.5 for example) to help with this and make sure that the binding redirects resolve back to the inbox System.Net.Http.dll binary. There have also been improvements to .NET Framework 4.7 and 4.7.1 and beyond to help resolve these mismatches better. |
I can't really comment on that because I don't have your complete Visual Studio solution. So, I can't trace thru all the possible references you have. But as long as you have a buildable solution now with binding redirects that work for you, then you should be good. |
Here is my repro solution. Something still feels very fishy about that 4.2.0.0 version getting brought in. |
I ran into the same problem, one of many with The problem seems to be that the libraries in: Conflict with the libraries in: Deleting the MSBuild version of the libraries enabled me to resolve the issue. It is perhaps worth noting that the MSBuild net47 library folder contains very few libraries and does not include As an alternative solution, I was also able to get things working by manually adding the right binding redirects. But for several reasons, feel that deleting the MSBuild version of the libraries is the better solution. I also tried AutoGenerateBindingRedirects and GenerateBindingRedirectsOutputType, but couldn't get those to work properly. Interestingly, I didn't get any of the expected compile time warnings about different library versions until I had deleted the MSBuild libraries. |
Well, I had all of this working. My project is targeting .NET Framework 4.7.1, and references a .NET Standard 2.0 library. Everything was happy until I upgraded from VS 15.4 to 15.5, now that redirect doesn't even work and I have to copy System.Net.Http.dll into the install location to get this rolling. |
I have been struggling with this issue as well. After installing VS 15.5, re-targeting the projects to .NET Framework 4.7.1 and changing to PackageReference instead of packages.config for nuget I get the 4.2.0.0 version of System.Net.Http.dll copied to the output folder. In my case the dependency on the System.Net.Http nuget package comes from using the newer System.Threading.Tasks.Dataflow from nuget. Turning on detailed logging gives me this:
and then
To me this behavior seems intentional, but I have yet to find some information online to support it. The automatically generated binding redirects are also consistent, redirecting 0.0.0.0 - 4.2.0.0 to 4.2.0.0. The only place where I still have to do manual redirects are for web applications. This is however not in line with what @davidsh wrote earlier - this assembly must be deployed for things to work, and it will be used instead of the assembly already present in .NET Framework 4.7.1. Can someone please confirm that ending up with 4.2.0.0 in this scenario is intended? (Btw, the title of this issue says v4.3.0.0, but I'm pretty sure that is incorrect and should be changed to v4.2.0.0. Debugging build problems in this scenario gets extremely difficult, since there is no correlation between the nuget package version, the assembly version or the file version.) |
Sorry you are correct the title had a typo and v4.2.0.0 is what is getting copied into the bin directory |
I've just upgraded an entire solution to 4.7.1 and I'm still seeing conflicts, but I don't know what exactly causes it.
First I thought 4.2.0.0 is only chosen when the project depends on a netstandard NuGet package, but it doesn't seem to make a difference. Below is the relevant build output:
@karelz is this issue on your radar? |
@davidsh I know OP is using net461, but I thought the binding redirects wouldn't be needed anymore with the combination of net471 and VS 15.5? Will .NET Framework 4.x need the binding redirects to 4.0.0.0 forever? Or is it only needed when a project does not reference one of Microsoft's packages that have the 4.2.0.0 version? |
The problem seems to be the existence of the MSBuild libraries, I think they are the wrong version, as surely they should match the Reference Assembly version. I was able to get all projects using the Reference Assemblies instead of the MSBuild libraries (without changing the actual dependencies), but after a while, it would revert to the MSBuild libraries. I was able to resolve the issue using binding redirects, but could not get AutoGenerateBindingRedirects to work. I abandoned this approach and simply deleted (moved) the MSBuild libraries, because the errors would happen at runtime (no errors at compile time) and I wasn't sure I had all the necessary binding redirects. |
@stijnherreman Well, it did work gloriously in net471 + netstardard20 for the few weeks that 15.3 was out. 15.4 turned around and broke it again :P |
I have finally managed to get our solution to build without getting any System.Net.Http.dll assemblies copied to the output folder, with no redirects and no removal of dlls from the build environment. I thought I should share some information about my findings if it helps investigating similar issues. As I mentioned earlier, we target .NET Framework 4.7.1 and use PackageReference to bring in the nuget packages. The problems for us started when we referenced the System.Threading.Tasks.Dataflow nuget package, v4.8.0. I have now found that moving back to v.4.7.0 of that package solves the problem. If we do that we no longer get any System.Net.Http.dll copied to the output folder and get to use the one already available as part of the framework. So what is different? I have a hunch that this is because the package dependencies are specified differently for these two versions. For v4.7.0, the nuget package specifically states ".NETFramework, Version=v4.5 No dependencies". But for v4.8.0, there is no longer anything explicitly stated for .NETFramework, only for .NETCoreApp, .NETStandard, .NETPortable and Xamarin of various versions. For example, it mentions ".NETStandard, Version=v2.0 No dependencies". Could it be that NuGet 4.3 and/or MSBuild 15.5 is failing to understand that .NETFramework completely fulfills .NETStandard 2.0? We also saw similar issues with the NUnit package version we used, v3.6.1. That package only lists dependencies for ".NETStardard, Version=v1.6", and using that causes (a different!) version of System.Net.Http.dll to appear in the output folder. Moving to v3.7.1, where ".NETFramework,Version=v4.5 No dependencies" is stated, System.Net.Http is correctly picked up from the framework and not copied to the output folder. So the problem seems to be nuget packages that does not specifically state their dependencies for .NET Framework. |
@weshaggard needs to answer this question. He is the subject matter expert on this topic. |
@AlexGhiondea @joperezr there seems to be a number of issues related to the tooling and support package throughout this thread. Can you please make sure that your current tooling fixes handle these cases? |
I hit the same issue. Full NET 4.7.1 project references netstandard2. I thought net471 fully supports netstandard2... |
Got the same issue again with another package. We used System.Buffers 4.4.0 in order to use ArrayPool, and that caused a strange 4.2.0.0 version of System.Diagnostics.Tracing.dll being copied to the output folder. Once again the workaround was to move back to 4.3.0 that states ".NETFramework,Version=v4.5 No dependencies", which version 4.4.0 does not do. So once again the problem seems to be nuget packages that does not specifically state their dependencies for .NET Framework. |
Setting property |
@onyxmaster Huh, if I understand dotnet/msbuild#2199 (should be part of 15.5 release) correctly, a similar property So that property fixed one issue but introduced another? |
Yes, I’ve seen the issue you mentioned, hence the warning that it might break something unknown. In my case (a 180+-project solution combining lots of legacy code) everything works okay, but probably because we do not reference any problematic nuget packages. I guess the outcome much depends on projects’ dependencies. |
I’m for sure looking for a proper fix for this, but it’s much more manageable for a team to add a property to a common property file shared among all projects (we have one, and even if we hadn’t, there is Directory.Build for that), than to remove the msbuild.extensions file on every build system :) |
My actual problem (linked above) is actually solvable by binding redirects, but I really hate when something breaks the established API contract (with exceptions, in my point of view, being the most important part of them, since they are discoverable only at runtime). |
It might, in fact, break some things if you set the property, which is why the temporary suggested solution is to add binding redirects. New changes have gone into the VS tooling that will be released on VS 15.6 Preview 3 that will generate the right binding redirects for you. For the time being, unfortunately, that needs to be done manually to fix these issues. |
Adding binding redirects doesn’t play well with projects that have automatic binding redirects enabled (test projects in our case), so I opted for the property. I have 15.6P2 installed, will test when/if P3 fixes the problem. Thanks for the heads-up! |
@joperezr Is it not an option to fix the offending packages that reference this 4.2.0.0 version? Either way, I sincerely hope that 15.6 will finally have resolved all problems. |
Same for us
…On Wed, Apr 4, 2018 at 5:33 AM armitagemderivitec ***@***.***> wrote:
@karelz <https://github.com/karelz> @joperezr
<https://github.com/joperezr> my issues are indeed with Asp.Net web
projects, we have both an API and MVC site with the issue
—
You are receiving this because you were mentioned.
Reply to this email directly, view it on GitHub
<https://github.com/dotnet/corefx/issues/25773#issuecomment-378555292>,
or mute the thread
<https://github.com/notifications/unsubscribe-auth/AAISTm3Y0O-dI-E3zNCWK0gUpamqhER6ks5tlKFygaJpZM4Q5EF8>
.
|
Thanks for confirmation @armitagemderivitec @jwisener. |
I'm seeing this issue as well (using VS 15.6.4). I have a .NET 4.7.1 class library referencing a nuget package that has a reference to a .NET Standard 2 component. The class library is referenced by a Windows Forms application, although I'm not sure that is relevant because these 12 System.* assemblies are deployed to the bin folder when only the class library is built. @rokleM 's suggestion of adding Does this align with everyone's findings? It seems like the general consensus is that this shouldn't be happening in the latest version of VS, but it is. Hopefully this helps someone. |
Thanks @karelz for the explanation. I will notify these two package maintainers who are including the NuGet package for System.Net.Http as a dependency. https://www.nuget.org/packages/Google.Apis/ |
@SamNutkins those 12 files present in the bin folder are expected if you are targeting 4.7.1. We have documented this as a known issue here. @joperezr will file a separate issue for the asp.net web projects issue. |
This is occurring for us in Service Fabric projects as well as ASP.NET projects (and the bindings need to be flipped if we run EntityFramework migrations in the Package Manager Console. Then flipped back if we want to run our app). Also, every time a package updates it reverts to a binding we DON'T want, it is super annoying and all of our developers are frustrated with it - myself included ;) |
Please fix, this is same problem for us. Running Service Fabric with Asp Net Core, the System.Net.Http (from C:\Program Files (x86)\Microsoft Visual Studio\2017\Enterprise\MSBuild\Microsoft\Microsoft.NET.Build.Extensions\net461\lib\System.Net.Http.dll) 4.2.0.0 overrides the latest 4.1.1.2 (from 4.3.3 System.Net.Http nuget package) |
@joperezr is Service Fabric the same problem, or do you need a new issue filed with new repro for investigation? |
From the first look it doesn't seem to be the same issue although it looks similar. @stevozilik do you mind opening a new issue with more info so we can take a look at your scenario? If you have minimal repro that would be ideal, but if not, try to at least include info like the framework you are targetting, VS you are using, and some info on the way you are publishing. Also getting details on the exception would help. |
Seeing the same issue in VS 15.7 Preview 5 using net461 class libraries and console applications. |
@eiriktsarpalis do you mind sharing a small repro so that we check what is going on? net461 shouldn't have this problem at all since the runtime facades have been injected successfully for many VS releases so I'm interested in understanding more about your scenario. |
Here's what I've learned from debugging this issue in a nontrivial codebase, in case it's helpful to others. The root cause of the issue is when you are targeting the desktop framework (e.g TargetFrameworkVersion=v.4.61) and you pick up a dependency on a Nuget package whose dependency metadata only includes dependency information for NetStandard. The bad package can be picked up either directly or transitively, which makes the root cause of these compile-time assembly resolution errors very difficult to isolate. In our case, we had picked up a transitive dependency on System.Buffers v4.4.0. The NuSpec for this version only contains Fortunately, this bug seems to have been noted and corrected in System.Buffers 4.5, which correctly declares dependencies for both NetStandard2.0 and .NETFramework4.5. We resolved the compile-time ambiguity by adding an explicit PackageReference to v4.5.0 of System.Buffers to override the transitive dependency on the bad version we had picked up through one of our direct dependencies. Because we were compiling against the correct version, we did not need to add any app.config assembly redirects to resolve ambiguity at runtime. It's not clear how many libraries beyond System.Buffers have this problem, but it's probably a non-zero set. If you're a library author and have a dependency on V4.4 of System.Buffers, all the people writing desktop apps against your library would greatly appreciate you moving to V4.5 as soon as possible :) |
I'm having the same issue, except I noticed that the output DLL from my project (ASP.NET Core 2) has a hard reference to 4.2.0.0 of System.Net.Http that I can see in .NET Reflector, even though I don't have a project reference to that at all. My project runs fine on my PC (naturally), and when deployed to Azure App Services (Azure Websites) it fails with that same error (I modified my project to instantiate an instance of
Screenshot proof:
Update:If I change my csproj (just for this ASP.NET Core 2 project) to target .NET Framework 4.7.1 instead of 4.7.2 and also add this to my csproj (so it builds), then it seems to work. I'm also able to remove the binding-redirect from web.config with no apparent ill-effects.
Fortunately I'm not using any of the new functionality in .NET 4.7.2. |
Why is the Visual Studio 2017 Build Tools for 4.7.1 version of the dll different from the nuget version of the file for 4.7.1? |
VS is different product than System.Net.Http nuget library (.NET tooling / IDE vs. .NET platform component, shipping from GitHub) |
@Jehoel what your issue tells me is that the server where your app is running doesn't have 4.7.2 installed. It may run fine on your machine because you do have 4.7.2 but the server must be on an earlier version of .NET. For regular console apps, we specify on the AppConfig the version of .NET that you target and when trying to load your app we ensure that this version is installed on the machine or we fail to load it, but Web Apps behave differently. |
@joperezr I'll admit that was my problem: I was deploying to Azure App Services which doesn't yet support 4.7.2, only 4.7.1 (progress in here: Azure/app-service-announcements-discussions#37) - but even when I manually copied the correct version of I accept (in my particular case, at least) it's primarily a PEBCAK-class problem with an RTFM solution. |
placing a version of an assembly and adding a binding redirect is in most cases not enough, since you would have to also copy all of the new assemblies that the new System.Net.Http assembly references and uses at runtime. Most of the framework is tightly coupled, which means that it is hard to just pick different pieces of it from different versions and expect things to just work. |
I resolved issue installing Microsoft.Rest.ClientRuntime package version 2.3.14 |
- Updated platform dependency to 2.13.53 for having System.Net.Http redirect. Otherwise Polly cannot be loaded on .Net 4.6.1: - App-vNext/Polly#668; - https://github.com/dotnet/corefx/issues/25773;
I have wasted endless days fighting this.. I just want to get back to coding please :( P.S i ended up making my own msbuild custom task to workaround most of its shortcomings (transitive deps, assembly resolution etc etc) |
This is still an absolute clusterfuck... and the rollout of .net 4.8 to azure appservice has introduced more problems. the EXACT same project (which has been fine for months without any changes) deployed to 2 different appservice plans now behaves differently. To make matters worse, scaling the appservice up/down often fixes the problem for a few days. I know you can't fix it - made clear by how long this doom-scroll of a thread is - but I hope others having this issue know they're not alone. |
This issue was mentioned in the following comment, but that thread seemed to deal primarily with a different scenario. @karelz requested a separate issue be filed and it doesn't seem that happened.
https://github.com/dotnet/corefx/issues/22781#issuecomment-322691420
The issue seems to be that when adding a reference to certain nuget packages, the version of System.Net.Http in the bin directory gets copied from
C:\Program Files (x86)\Microsoft Visual Studio\2017\Enterprise\MSBuild\Microsoft\Microsoft.NET.Build.Extensions\net461\lib\System.Net.Http.dll which is a later version than what is available on nuget.
Here is the simplest repro I could come up with:
a. Version of System.Net.Http in both bin directories is v4.1.1.2 dated 9/5/2017.
b. If you look at the System.Net.Http reference in the VS properties window of solution explorer, it will show the version as 4.1.1.2.
c. In the properties window ClassLibrary1 shows the path {solution_dir}\packages\System.Net.Http.4.3.3\lib\net46\System.Net.Http.dll
a. Building will generate the warning "Found conflicts between different versions of 'System.Net.Http' that could not be resolved"
b. Running the app will generate a run-time exception: "Unhandled Exception: System.IO.FileLoadException: Could not load file or assembly 'System.Net.Http, Version=4.2.0.0"
c. Version of System.Net.Http in the ClassLibrary1 bin directory is v4.2.0.0 and dated 12/4/2017
d. The reference properties window in VS for ClassLibrary1 shows the path as C:\Program Files (x86)\Microsoft Visual Studio\2017\Enterprise\MSBuild\Microsoft\Microsoft.NET.Build.Extensions\net461\lib\System.Net.Http.dll
In short, for some reason after adding nuget package for System.Collections.Immutable v1.4.0, the MSBuild version of System.Net.Http seems to get introduced into the project and causes problems.
I don't know if System.Collections.Immutable is unique in triggering this scenario. The previous issue/comment suggests that other packages might also trigger this (System.Threading.Tasks.Dataflow)
I can work around this issue with the following binding redirect:
But it seems incorrect to have to redirect backwards like that.
The text was updated successfully, but these errors were encountered: