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

Improve MSBuild SDK resolver by parsing global.json with System.Runtime.Serialization.Json #3157

Merged
merged 3 commits into from
Jan 13, 2020

Conversation

jeffkl
Copy link
Contributor

@jeffkl jeffkl commented Dec 10, 2019

This is a proposed replacement of #2879. This PR uses a built-in class to read global.json so we still get validation of the file's schema but we don't need to load Newtonsoft.Json and other assemblies.

The perf gain isn't as great as using a Regex but it does reduce the resolve time from ~288ms to 100ms.

Bug

Addresses: dotnet/msbuild#4025
Regression: No

  • Last working version:
  • How are we preventing it in future:

Fix

Details: Use the built-in System.Runtime.Serialization.Json.JsonReaderWriterFactory to read global.json instead of Newtonsoft.Json. The built-in libraries are always NGen'd/CrossGen'd and will load faster.

I also cleaned up the unit tests to use NuGet's built in test utility instead of the one we added when the SDK resolver was copied here from the MSBuild repo

Testing/Validation

Tests Added: Yes
Reason for not adding tests:
Validation:

Copy link
Member

@zivkan zivkan left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think the PR title is wrong. It's using System.Runtime.Serialization.Json, not System.Xml. The Json APIs might use types from System.Xml, but we're not using XML APIs to read the JSON file.

{
return string.IsNullOrEmpty(path) || Path.DirectorySeparatorChar == '\\' ? path : path.Replace('\\', '/');
using (var stream = new FileStream(path, FileMode.Open, FileAccess.Read, FileShare.Read))
using (var reader = System.Runtime.Serialization.Json.JsonReaderWriterFactory.CreateJsonReader(stream, XmlDictionaryReaderQuotas.Max))
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Given NuGet is already targeting .NET Core 3.1 and later, is there a benefit to using System.Text.Json's JsonReader instead?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For .NET Framework, we'd need to ship a separate assembly which I don't think would JIT as fast. The size of global.json is very small and so the performance gain mainly comes from not having to load a big DLL to read it. So I think System.Text.Json would probably not be a good candidate for this. Ideally we'd use some native library to read it so its even faster.

@jeffkl
Copy link
Contributor Author

jeffkl commented Dec 16, 2019

I think the PR title is wrong. It's using System.Runtime.Serialization.Json, not System.Xml. The Json APIs might use types from System.Xml, but we're not using XML APIs to read the JSON file.

Its definitely confusing. I'm using JsonReaderWriterFactory which returns an XmlJsonReader that implements an XmlReader from System.Xml. You end up calling the same methods as if you're reading an XML file while under the covers its reading it as JSON. So I titled this with "reading JSON via System.Xml". I'm more than happy to rename it

This uses the System.Runtime.Serialization.Json.JsonReaderWriterFactory to load global.json
Delete redundant TestEnvironment class in favor of our own TestDirectory class
@jeffkl jeffkl force-pushed the parse-global-json-with-system-xml branch from 40a33b8 to 505baf9 Compare January 9, 2020 23:04
@jeffkl jeffkl changed the title Improve MSBuild SDK resolver by parsing global.json with System.Xml Improve MSBuild SDK resolver by parsing global.json with System.Runtime.Serialization.Json Jan 9, 2020
@jeffkl
Copy link
Contributor Author

jeffkl commented Jan 9, 2020

@zivkan and @nkolev92 please review at your earliest convenience

Copy link
Member

@nkolev92 nkolev92 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

@@ -1,1301 +0,0 @@
// Copyright (c) .NET Foundation. All rights reserved.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🔪

@jeffkl jeffkl merged commit 5a3eeab into NuGet:dev Jan 13, 2020
@jeffkl jeffkl deleted the parse-global-json-with-system-xml branch January 13, 2020 15:55
jeffkl added a commit to jeffkl/NuGet.Client that referenced this pull request Jan 24, 2020
…em.Runtime.Serialization.Json (NuGet#3157)"

This reverts commit 5a3eeab.
jeffkl added a commit that referenced this pull request Jan 24, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
5 participants