From 34ef7159534ae7872206ef4149b8581dbc5d7014 Mon Sep 17 00:00:00 2001 From: Tom Meschter Date: Thu, 9 Mar 2017 15:32:03 -0800 Subject: Add a missing scenario for Framework injection Whenever a UWP app contains managed code we need to be sure to inject the .NET Core Framework assemblies. This is obviously the case when the app itself is written in C# or VB. However, we also need to handle the case where the app is written in C++ but references a WinRT component written in managed code. We detect the latter case by looking for the use of the union Windows.winmd assembly. We assume the assembly is in a path that ends with "UnionMetadata\Windows.winmd", but this isn't always the case. Sometimes the path will include the Windows SDK version number, like "UnionMetadata\10.0.15000.0\Windows.winmd"; in this case we won't realize that the framework is needed, and .NET Native compilation will fail. The fix here is to check for these other locations by making use of the WindowsSDK_UnionMetadataPath property. --- src/Microsoft.NuGet.Build.Tasks/Microsoft.NuGet.targets | 1 + 1 file changed, 1 insertion(+) diff --git a/src/Microsoft.NuGet.Build.Tasks/Microsoft.NuGet.targets b/src/Microsoft.NuGet.Build.Tasks/Microsoft.NuGet.targets index f56dfca..54ed535 100644 --- a/src/Microsoft.NuGet.Build.Tasks/Microsoft.NuGet.targets +++ b/src/Microsoft.NuGet.Build.Tasks/Microsoft.NuGet.targets @@ -284,6 +284,7 @@ Copyright (c) .NET Foundation. All rights reserved. <_PackagingOutputsIncludesFramework Condition="'%(PackagingOutputs.FileName)%(PackagingOutputs.Extension)' == 'System.Runtime.dll'">true <_AppContainsManagedCodeForInjection Condition="'%(PackagingOutputs.Identity)' == '$(_TargetPlatformSdkDir)UnionMetadata\Windows.winmd'">true + <_AppContainsManagedCodeForInjection Condition="'%(PackagingOutputs.Identity)' == '$(WindowsSDK_UnionMetadataPath)\Windows.winmd'">true -- cgit v1.2.3 From 42b97d978be258bbf915e56bb69747bc8956a3af Mon Sep 17 00:00:00 2001 From: Zhi Li Date: Tue, 21 Feb 2017 14:21:20 -0800 Subject: removed xproj project reference --- .../Microsoft.NuGet.Build.Tasks.Tests.csproj | 1 - .../NuGetTestHelpers.cs | 2 - .../LockFileWithXProjReference.json | 41 --------------- .../ProjectReferences/ProjectReferenceTests.cs | 39 --------------- .../ProjectReferences/Resources.Designer.cs | 28 ----------- .../ProjectReferences/Resources.resx | 3 -- .../Microsoft.NuGet.targets | 20 -------- .../NuGetPackageObject.cs | 4 +- .../ResolveNuGetPackageAssets.cs | 58 ++-------------------- .../Strings.Designer.cs | 9 ---- src/Microsoft.NuGet.Build.Tasks/Strings.resx | 3 -- 11 files changed, 5 insertions(+), 203 deletions(-) delete mode 100644 src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/LockFileWithXProjReference.json diff --git a/src/Microsoft.NuGet.Build.Tasks.Tests/Microsoft.NuGet.Build.Tasks.Tests.csproj b/src/Microsoft.NuGet.Build.Tasks.Tests/Microsoft.NuGet.Build.Tasks.Tests.csproj index bc77c93..2f0c78e 100644 --- a/src/Microsoft.NuGet.Build.Tasks.Tests/Microsoft.NuGet.Build.Tasks.Tests.csproj +++ b/src/Microsoft.NuGet.Build.Tasks.Tests/Microsoft.NuGet.Build.Tasks.Tests.csproj @@ -86,7 +86,6 @@ - diff --git a/src/Microsoft.NuGet.Build.Tasks.Tests/NuGetTestHelpers.cs b/src/Microsoft.NuGet.Build.Tasks.Tests/NuGetTestHelpers.cs index 690a64d..f31e9d0 100644 --- a/src/Microsoft.NuGet.Build.Tasks.Tests/NuGetTestHelpers.cs +++ b/src/Microsoft.NuGet.Build.Tasks.Tests/NuGetTestHelpers.cs @@ -26,7 +26,6 @@ namespace Microsoft.NuGet.Build.Tasks.Tests TryGetRuntimeVersion tryGetRuntimeVersion = null, bool includeFrameworkReferences = true, string projectJsonFileContents = null, - IEnumerable projectReferencesCreatingPackages = null, bool createTemporaryFolderForPackages = true) { var rootDirectory = new TempRoot(); @@ -79,7 +78,6 @@ namespace Microsoft.NuGet.Build.Tasks.Tests task.IncludeFrameworkReferences = includeFrameworkReferences; task.NuGetPackagesDirectory = packagesDirectory?.Path; task.RuntimeIdentifier = runtimeIdentifier; - task.ProjectReferencesCreatingPackages = (projectReferencesCreatingPackages ?? Enumerable.Empty()).ToArray(); task.ProjectLockFile = projectLockJsonFile.Path; task.ProjectLanguage = projectLanguage; task.TargetMonikers = new ITaskItem[] { new TaskItem(targetMoniker) }; diff --git a/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/LockFileWithXProjReference.json b/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/LockFileWithXProjReference.json deleted file mode 100644 index c4970b6..0000000 --- a/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/LockFileWithXProjReference.json +++ /dev/null @@ -1,41 +0,0 @@ -{ - "locked": false, - "version": 2, - "targets": { - ".NETFramework,Version=v4.5.2": { - "XProjClassLib/1.0.0": { - "type": "project", - "framework": ".NETFramework,Version=v4.5.2", - "compile": { - "net452/XProjClassLib.dll": { } - }, - "runtime": { - "net452/XProjClassLib.dll": { } - } - } - }, - ".NETFramework,Version=v4.5.2/win": { - "XProjClassLib/1.0.0": { - "type": "project", - "framework": ".NETFramework,Version=v4.5.2", - "compile": { - "net452/XProjClassLib.dll": { } - }, - "runtime": { - "net452/XProjClassLib.dll": { } - } - } - } - }, - "libraries": { - "XProjClassLib/1.0.0": { - "type": "project", - "path": "../XProjClassLib/project.json", - "msbuildProject": "../XProjClassLib/XProjClassLib.xproj" - } - }, - "projectFileDependencyGroups": { - "": [ ], - ".NETFramework,Version=v4.5.2": [ ] - } -} \ No newline at end of file diff --git a/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/ProjectReferenceTests.cs b/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/ProjectReferenceTests.cs index 3460343..cb87fcc 100644 --- a/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/ProjectReferenceTests.cs +++ b/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/ProjectReferenceTests.cs @@ -10,45 +10,6 @@ namespace Microsoft.NuGet.Build.Tasks.Tests.ProjectReferences { public class ProjectReferenceTests { - [Fact] - public void ProjectReferenceToXProjWithAssetsButNotWithAPathFails() - { - var exception = Assert.Throws( - () => NuGetTestHelpers.ResolvePackagesWithJsonFileContents(Resources.LockFileWithXProjReference, ".NETFramework,Version=v4.5.2", "win")); - - Assert.Equal(nameof(Strings.MissingProjectReference), exception.ResourceName); - AssertHelpers.PathEndsWith(@"XProjClassLib\XProjClassLib.xproj", exception.MessageArgs[0]); - } - - [Fact] - public void ProjectReferenceToProjectWithNoMSBuildProjectFailsGracefully() - { - var exception = Assert.Throws( - () => NuGetTestHelpers.ResolvePackagesWithJsonFileContents(Resources.LockFileMissingMSBuildProjectThatProvidesAssets, ".NETFramework,Version=v4.5.2", "win")); - - Assert.Equal(nameof(Strings.MissingMSBuildPathInProjectPackage), exception.ResourceName); - Assert.Equal(@"XProjClassLib", exception.MessageArgs[0]); - } - - [Fact] - public void ProjectReferenceToXProjWithAssetsAndPathSucceeds() - { - var referenceToXProj = new TaskItem(@"..\XProjClassLib\XProjClassLib.xproj"); - referenceToXProj.SetMetadata("OutputBasePath", "XProjOutputDirectory"); - - var result = NuGetTestHelpers.ResolvePackagesWithJsonFileContents( - Resources.LockFileWithXProjReference, - ".NETFramework,Version=v4.5.2", - "win", - projectReferencesCreatingPackages: new[] { referenceToXProj }); - - Assert.Empty(result.Analyzers); - AssertHelpers.PathEndsWith(@"XProjOutputDirectory\net452\XProjClassLib.dll", result.CopyLocalItems.Single().ItemSpec); - AssertHelpers.PathEndsWith(@"XProjOutputDirectory\net452\XProjClassLib.dll", result.References.Single().ItemSpec); - Assert.All(result.References, r => Assert.Equal(ResolveNuGetPackageAssets.NuGetSourceType_Project, r.GetMetadata(ResolveNuGetPackageAssets.NuGetSourceType))); - Assert.Empty(result.ReferencedPackages); - } - [Fact] public void ProjectReferenceToCSProjWithoutAssetsAndNoPathSucceeds() { diff --git a/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/Resources.Designer.cs b/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/Resources.Designer.cs index a966927..1af74df 100644 --- a/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/Resources.Designer.cs +++ b/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/Resources.Designer.cs @@ -116,33 +116,5 @@ namespace Microsoft.NuGet.Build.Tasks.Tests.ProjectReferences { return ResourceManager.GetString("LockFileWithCSProjReference", resourceCulture); } } - - /// - /// Looks up a localized string similar to { - /// "locked": false, - /// "version": 2, - /// "targets": { - /// ".NETFramework,Version=v4.5.2": { - /// "XProjClassLib/1.0.0": { - /// "type": "project", - /// "framework": ".NETFramework,Version=v4.5.2", - /// "compile": { - /// "net452/XProjClassLib.dll": { } - /// }, - /// "runtime": { - /// "net452/XProjClassLib.dll": { } - /// } - /// } - /// }, - /// ".NETFramework,Version=v4.5.2/win": { - /// "XProjClassLib/1.0.0": { - /// "type": "project", - /// "framework": ".NETFram [rest of string was truncated]";. - /// - internal static string LockFileWithXProjReference { - get { - return ResourceManager.GetString("LockFileWithXProjReference", resourceCulture); - } - } } } diff --git a/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/Resources.resx b/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/Resources.resx index 945ce91..89629ca 100644 --- a/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/Resources.resx +++ b/src/Microsoft.NuGet.Build.Tasks.Tests/ProjectReferences/Resources.resx @@ -124,7 +124,4 @@ lockfilewithcsprojreference.json;System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089;utf-8 - - lockfilewithxprojreference.json;System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089;utf-8 - \ No newline at end of file diff --git a/src/Microsoft.NuGet.Build.Tasks/Microsoft.NuGet.targets b/src/Microsoft.NuGet.Build.Tasks/Microsoft.NuGet.targets index f56dfca..fe56d26 100644 --- a/src/Microsoft.NuGet.Build.Tasks/Microsoft.NuGet.targets +++ b/src/Microsoft.NuGet.Build.Tasks/Microsoft.NuGet.targets @@ -175,25 +175,6 @@ Copyright (c) .NET Foundation. All rights reserved. DependsOnTargets="$(ResolveNuGetPackageAssetsDependsOn)" Condition="'$(ResolveNuGetPackages)' == 'true' and exists('$(ProjectLockFile)')"> - - - - - - - - - - %(_XProjTargetDirs.Identity) - - - diff --git a/src/Microsoft.NuGet.Build.Tasks/NuGetPackageObject.cs b/src/Microsoft.NuGet.Build.Tasks/NuGetPackageObject.cs index b6fb6fc..696db15 100644 --- a/src/Microsoft.NuGet.Build.Tasks/NuGetPackageObject.cs +++ b/src/Microsoft.NuGet.Build.Tasks/NuGetPackageObject.cs @@ -23,11 +23,10 @@ namespace Microsoft.NuGet.Build.Tasks /// private readonly Lazy _fullPackagePath; - public NuGetPackageObject(string id, string version, bool isProject, Func fullPackagePathGenerator, JObject targetObject, JObject libraryObject) + public NuGetPackageObject(string id, string version, Func fullPackagePathGenerator, JObject targetObject, JObject libraryObject) { Id = id; Version = version; - IsProject = isProject; _fullPackagePath = new Lazy(fullPackagePathGenerator); TargetObject = targetObject; LibraryObject = libraryObject; @@ -35,7 +34,6 @@ namespace Microsoft.NuGet.Build.Tasks public string Id { get; } public string Version { get; } - public bool IsProject { get; } /// /// The JSON object from the "targets" section in the project.lock.json for this package. diff --git a/src/Microsoft.NuGet.Build.Tasks/ResolveNuGetPackageAssets.cs b/src/Microsoft.NuGet.Build.Tasks/ResolveNuGetPackageAssets.cs index de16d88..3e12fb0 100644 --- a/src/Microsoft.NuGet.Build.Tasks/ResolveNuGetPackageAssets.cs +++ b/src/Microsoft.NuGet.Build.Tasks/ResolveNuGetPackageAssets.cs @@ -23,7 +23,6 @@ namespace Microsoft.NuGet.Build.Tasks internal const string NuGetPackageVersionMetadata = "NuGetPackageVersion"; internal const string NuGetIsFrameworkReference = "NuGetIsFrameworkReference"; internal const string NuGetSourceType = "NuGetSourceType"; - internal const string NuGetSourceType_Project = "Project"; internal const string NuGetSourceType_Package = "Package"; internal const string ReferenceImplementationMetadata = "Implementation"; @@ -46,8 +45,6 @@ namespace Microsoft.NuGet.Build.Tasks private readonly List _packageFolders = new List(); - private readonly Dictionary _projectReferencesToOutputBasePaths = new Dictionary(StringComparer.OrdinalIgnoreCase); - #region UnitTestSupport private readonly FileExists _fileExists = new FileExists(File.Exists); private readonly TryGetRuntimeVersion _tryGetRuntimeVersion = new TryGetRuntimeVersion(TryGetRuntimeVersion); @@ -142,15 +139,6 @@ namespace Microsoft.NuGet.Build.Tasks get; set; } - /// - /// A list of project references that are creating packages as listed in the lock file. The OutputPath metadata should - /// set on each of these items, which is used by the task to construct full output paths to assets. - /// - public ITaskItem[] ProjectReferencesCreatingPackages - { - get; set; - } - /// /// The base output directory where the temporary, preprocessed files should be written to. /// @@ -238,7 +226,6 @@ namespace Microsoft.NuGet.Build.Tasks PopulatePackageFolders(lockFile); - PopulateProjectReferenceMaps(); GetReferences(lockFile); GetCopyLocalItems(lockFile); GetAnalyzers(lockFile); @@ -281,23 +268,6 @@ namespace Microsoft.NuGet.Build.Tasks } } - private void PopulateProjectReferenceMaps() - { - foreach (var projectReference in ProjectReferencesCreatingPackages ?? new ITaskItem[] { }) - { - var fullPath = GetAbsolutePathFromProjectRelativePath(projectReference.ItemSpec); - if (_projectReferencesToOutputBasePaths.ContainsKey(fullPath)) - { - Log.LogWarningFromResources(nameof(Strings.DuplicateProjectReference), fullPath, nameof(ProjectReferencesCreatingPackages)); - } - else - { - var outputPath = projectReference.GetMetadata("OutputBasePath"); - _projectReferencesToOutputBasePaths.Add(fullPath, outputPath); - } - } - } - private void GetReferences(JObject lockFile) { var target = GetTargetOrAttemptFallback(lockFile, needsRuntimeIdentifier: false); @@ -820,7 +790,7 @@ namespace Microsoft.NuGet.Build.Tasks item.SetMetadata("Private", "false"); item.SetMetadata(NuGetIsFrameworkReference, "false"); - item.SetMetadata(NuGetSourceType, package.IsProject ? NuGetSourceType_Project : NuGetSourceType_Package); + item.SetMetadata(NuGetSourceType, NuGetSourceType_Package); items.Add(item); @@ -939,7 +909,6 @@ namespace Microsoft.NuGet.Build.Tasks var nameParts = package.Key.Split('/'); var id = nameParts[0]; var version = nameParts[1]; - bool isProject = false; var libraryObject = (JObject)lockFile["libraries"][package.Key]; @@ -951,35 +920,16 @@ namespace Microsoft.NuGet.Build.Tasks } // If this is a project then we need to figure out it's relative output path - if ((string)libraryObject["type"] == "project") + if ("project".Equals((string)libraryObject["type"], StringComparison.OrdinalIgnoreCase)) { - isProject = true; - - fullPackagePathGenerator = () => - { - var relativeMSBuildProjectPath = (string)libraryObject["msbuildProject"]; - - if (string.IsNullOrEmpty(relativeMSBuildProjectPath)) - { - throw new ExceptionFromResource(nameof(Strings.MissingMSBuildPathInProjectPackage), id); - } - - var absoluteMSBuildProjectPath = GetAbsolutePathFromProjectRelativePath(relativeMSBuildProjectPath); - string fullPackagePath; - if (!_projectReferencesToOutputBasePaths.TryGetValue(absoluteMSBuildProjectPath, out fullPackagePath)) - { - throw new ExceptionFromResource(nameof(Strings.MissingProjectReference), absoluteMSBuildProjectPath, nameof(ProjectReferencesCreatingPackages)); - } - - return fullPackagePath; - }; + continue; } else { fullPackagePathGenerator = () => GetNuGetPackagePath(id, version); } - yield return new NuGetPackageObject(id, version, isProject, fullPackagePathGenerator, (JObject)package.Value, libraryObject); + yield return new NuGetPackageObject(id, version, fullPackagePathGenerator, (JObject)package.Value, libraryObject); } } diff --git a/src/Microsoft.NuGet.Build.Tasks/Strings.Designer.cs b/src/Microsoft.NuGet.Build.Tasks/Strings.Designer.cs index 6d71ed9..9b3de63 100644 --- a/src/Microsoft.NuGet.Build.Tasks/Strings.Designer.cs +++ b/src/Microsoft.NuGet.Build.Tasks/Strings.Designer.cs @@ -69,15 +69,6 @@ namespace Microsoft.NuGet.Build.Tasks { } } - /// - /// Looks up a localized string similar to The project '{0}' was referenced more than once in the {1} property. Ignoring all but the first.. - /// - internal static string DuplicateProjectReference { - get { - return ResourceManager.GetString("DuplicateProjectReference", resourceCulture); - } - } - /// /// Looks up a localized string similar to Lock file {0} couldn't be found. Run a NuGet package restore to generate this file.. /// diff --git a/src/Microsoft.NuGet.Build.Tasks/Strings.resx b/src/Microsoft.NuGet.Build.Tasks/Strings.resx index 03a7fd1..16d5d64 100644 --- a/src/Microsoft.NuGet.Build.Tasks/Strings.resx +++ b/src/Microsoft.NuGet.Build.Tasks/Strings.resx @@ -120,9 +120,6 @@ The preprocessor token '{0}' has been given more than one value. Choosing '{1}' as the value. - - The project '{0}' was referenced more than once in the {1} property. Ignoring all but the first. - Lock file {0} couldn't be found. Run a NuGet package restore to generate this file. -- cgit v1.2.3 From dadda09b824f959dc21557a22645c1500faf9d45 Mon Sep 17 00:00:00 2001 From: Tom Meschter Date: Tue, 14 Mar 2017 12:47:58 -0700 Subject: Don't show project references as package references in Solution Explorer When a NuGet restore generates a project.assets.json file it includes information not only on which NuGet packages are used by a project, but which other projects are referenced as well. When reading the list of dependencies from project.assets.json we currently make no distinction between a _package_ dependency versus a _project_ dependency. The result is that projects get included with the list of packages we show in the Solution Explorer under the References node--and since the language service already shows project references there, we end up with two nodes representing the same thing. The fix here is to filter out the project dependency in the build task. For every dependency, we check it against the items in the "library" section of the project.assets.json file. This specifies whether a particular "library" comes from a project or a package. If it does not explicitly state that it is a project, we assume it is a package. A unit test has been added to cover this scenario. --- .../Json/Json.Designer.cs | 29 +++ .../Json/Json.resx | 3 + .../Json/ProjectDependency.assets.json | 213 +++++++++++++++++++++ .../Microsoft.NuGet.Build.Tasks.Tests.csproj | 1 + .../ReferenceResolutionTests.cs | 11 ++ .../Microsoft.NuGet.Build.Tasks.csproj | 2 +- .../ResolveNuGetPackageAssets.cs | 52 ++++- 7 files changed, 303 insertions(+), 8 deletions(-) create mode 100644 src/Microsoft.NuGet.Build.Tasks.Tests/Json/ProjectDependency.assets.json diff --git a/src/Microsoft.NuGet.Build.Tasks.Tests/Json/Json.Designer.cs b/src/Microsoft.NuGet.Build.Tasks.Tests/Json/Json.Designer.cs index eeed7e7..f0345cb 100644 --- a/src/Microsoft.NuGet.Build.Tasks.Tests/Json/Json.Designer.cs +++ b/src/Microsoft.NuGet.Build.Tasks.Tests/Json/Json.Designer.cs @@ -231,6 +231,35 @@ namespace Microsoft.NuGet.Build.Tasks.Tests.Json { } } + /// + /// Looks up a localized string similar to { + /// "version": 2, + /// "targets": { + /// ".NETFramework,Version=v4.5.2": { + /// "log4net/2.0.7": { + /// "type": "package", + /// "compile": { + /// "lib/net45-full/log4net.dll": {} + /// }, + /// "runtime": { + /// "lib/net45-full/log4net.dll": {} + /// } + /// }, + /// "Newtonsoft.Json/9.0.1": { + /// "type": "package", + /// "compile": { + /// "lib/net45/Newtonsoft.Json.dll": {} + /// }, + /// "runtime": { + /// "lib/net45/Newtonsoft.Json.dll": {} + /// [rest of string was truncated]";. + /// + internal static string ProjectDependency { + get { + return ResourceManager.GetString("ProjectDependency", resourceCulture); + } + } + /// /// Looks up a localized string similar to { /// "locked": false, diff --git a/src/Microsoft.NuGet.Build.Tasks.Tests/Json/Json.resx b/src/Microsoft.NuGet.Build.Tasks.Tests/Json/Json.resx index e2273cf..a59102f 100644 --- a/src/Microsoft.NuGet.Build.Tasks.Tests/Json/Json.resx +++ b/src/Microsoft.NuGet.Build.Tasks.Tests/Json/Json.resx @@ -145,4 +145,7 @@ multipleprojectfiledependencygroups.json;System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089;utf-8 + + ProjectDependency.assets.json;System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089;utf-8 + \ No newline at end of file diff --git a/src/Microsoft.NuGet.Build.Tasks.Tests/Json/ProjectDependency.assets.json b/src/Microsoft.NuGet.Build.Tasks.Tests/Json/ProjectDependency.assets.json new file mode 100644 index 0000000..c718a5a --- /dev/null +++ b/src/Microsoft.NuGet.Build.Tasks.Tests/Json/ProjectDependency.assets.json @@ -0,0 +1,213 @@ +{ + "version": 2, + "targets": { + ".NETFramework,Version=v4.5.2": { + "log4net/2.0.7": { + "type": "package", + "compile": { + "lib/net45-full/log4net.dll": {} + }, + "runtime": { + "lib/net45-full/log4net.dll": {} + } + }, + "Newtonsoft.Json/9.0.1": { + "type": "package", + "compile": { + "lib/net45/Newtonsoft.Json.dll": {} + }, + "runtime": { + "lib/net45/Newtonsoft.Json.dll": {} + } + }, + "ClassLibrary1/1.0.0": { + "type": "project" + } + }, + ".NETFramework,Version=v4.5.2/win": { + "log4net/2.0.7": { + "type": "package", + "compile": { + "lib/net45-full/log4net.dll": {} + }, + "runtime": { + "lib/net45-full/log4net.dll": {} + } + }, + "Newtonsoft.Json/9.0.1": { + "type": "package", + "compile": { + "lib/net45/Newtonsoft.Json.dll": {} + }, + "runtime": { + "lib/net45/Newtonsoft.Json.dll": {} + } + }, + "ClassLibrary1/1.0.0": { + "type": "project" + } + }, + ".NETFramework,Version=v4.5.2/win-x64": { + "log4net/2.0.7": { + "type": "package", + "compile": { + "lib/net45-full/log4net.dll": {} + }, + "runtime": { + "lib/net45-full/log4net.dll": {} + } + }, + "Newtonsoft.Json/9.0.1": { + "type": "package", + "compile": { + "lib/net45/Newtonsoft.Json.dll": {} + }, + "runtime": { + "lib/net45/Newtonsoft.Json.dll": {} + } + }, + "ClassLibrary1/1.0.0": { + "type": "project" + } + }, + ".NETFramework,Version=v4.5.2/win-x86": { + "log4net/2.0.7": { + "type": "package", + "compile": { + "lib/net45-full/log4net.dll": {} + }, + "runtime": { + "lib/net45-full/log4net.dll": {} + } + }, + "Newtonsoft.Json/9.0.1": { + "type": "package", + "compile": { + "lib/net45/Newtonsoft.Json.dll": {} + }, + "runtime": { + "lib/net45/Newtonsoft.Json.dll": {} + } + }, + "ClassLibrary1/1.0.0": { + "type": "project" + } + } + }, + "libraries": { + "log4net/2.0.7": { + "sha512": "9zY5lPFy4ppjeaTKwHjXbHe6lhle64Bnwui3YDEnnlo4NzHcUE9/h4BqCn3PCCvYbpwO4+ceWdqk9J/lxrQ9dQ==", + "type": "package", + "path": "log4net/2.0.7", + "files": [ + "lib/net20-full/log4net.dll", + "lib/net20-full/log4net.xml", + "lib/net35-client/log4net.dll", + "lib/net35-client/log4net.xml", + "lib/net35-full/log4net.dll", + "lib/net35-full/log4net.xml", + "lib/net40-client/log4net.dll", + "lib/net40-client/log4net.xml", + "lib/net40-full/log4net.dll", + "lib/net40-full/log4net.xml", + "lib/net45-full/log4net.dll", + "lib/net45-full/log4net.xml", + "lib/netstandard1.3/log4net.dll", + "log4net.2.0.7.nupkg.sha512", + "log4net.nuspec" + ] + }, + "Newtonsoft.Json/9.0.1": { + "sha512": "U82mHQSKaIk+lpSVCbWYKNavmNH1i5xrExDEquU1i6I5pV6UMOqRnJRSlKO3cMPfcpp0RgDY+8jUXHdQ4IfXvw==", + "type": "package", + "path": "newtonsoft.json/9.0.1", + "files": [ + "lib/net20/Newtonsoft.Json.dll", + "lib/net20/Newtonsoft.Json.xml", + "lib/net35/Newtonsoft.Json.dll", + "lib/net35/Newtonsoft.Json.xml", + "lib/net40/Newtonsoft.Json.dll", + "lib/net40/Newtonsoft.Json.xml", + "lib/net45/Newtonsoft.Json.dll", + "lib/net45/Newtonsoft.Json.xml", + "lib/netstandard1.0/Newtonsoft.Json.dll", + "lib/netstandard1.0/Newtonsoft.Json.xml", + "lib/portable-net40+sl5+wp80+win8+wpa81/Newtonsoft.Json.dll", + "lib/portable-net40+sl5+wp80+win8+wpa81/Newtonsoft.Json.xml", + "lib/portable-net45+wp80+win8+wpa81/Newtonsoft.Json.dll", + "lib/portable-net45+wp80+win8+wpa81/Newtonsoft.Json.xml", + "newtonsoft.json.9.0.1.nupkg.sha512", + "newtonsoft.json.nuspec", + "tools/install.ps1" + ] + }, + "ClassLibrary1/1.0.0": { + "type": "project", + "path": "../ClassLibrary1/ClassLibrary1.csproj", + "msbuildProject": "../ClassLibrary1/ClassLibrary1.csproj" + } + }, + "projectFileDependencyGroups": { + ".NETFramework,Version=v4.5.2": [ + "ClassLibrary1 >= 1.0.0", + "Newtonsoft.Json >= 9.0.1", + "log4net >= 2.0.7" + ] + }, + "packageFolders": { + "C:\\Users\\tomescht\\.nuget\\packages\\": {} + }, + "project": { + "version": "1.0.0", + "restore": { + "projectUniqueName": "C:\\Users\\tomescht\\Documents\\Visual Studio 2017\\Projects\\WpfApp1\\WpfApp1\\WpfApp1.csproj", + "projectName": "WpfApp1", + "projectPath": "C:\\Users\\tomescht\\Documents\\Visual Studio 2017\\Projects\\WpfApp1\\WpfApp1\\WpfApp1.csproj", + "outputPath": "C:\\Users\\tomescht\\Documents\\Visual Studio 2017\\Projects\\WpfApp1\\WpfApp1\\obj\\", + "projectStyle": "PackageReference", + "originalTargetFrameworks": [ + "net452" + ], + "frameworks": { + "net452": { + "projectReferences": { + "C:\\Users\\tomescht\\Documents\\Visual Studio 2017\\Projects\\WpfApp1\\ClassLibrary1\\ClassLibrary1.csproj": { + "projectPath": "C:\\Users\\tomescht\\Documents\\Visual Studio 2017\\Projects\\WpfApp1\\ClassLibrary1\\ClassLibrary1.csproj" + } + } + } + } + }, + "dependencies": { + "Newtonsoft.Json": { + "target": "Package", + "version": "9.0.1" + }, + "log4net": { + "target": "Package", + "version": "[2.0.7, )" + } + }, + "frameworks": { + "net452": { + "dependencies": { + "Newtonsoft.Json": { + "target": "Package", + "version": "9.0.1" + } + } + } + }, + "runtimes": { + "win": { + "#import": [] + }, + "win-x64": { + "#import": [] + }, + "win-x86": { + "#import": [] + } + } + } +} \ No newline at end of file diff --git a/src/Microsoft.NuGet.Build.Tasks.Tests/Microsoft.NuGet.Build.Tasks.Tests.csproj b/src/Microsoft.NuGet.Build.Tasks.Tests/Microsoft.NuGet.Build.Tasks.Tests.csproj index 2f0c78e..ccf4463 100644 --- a/src/Microsoft.NuGet.Build.Tasks.Tests/Microsoft.NuGet.Build.Tasks.Tests.csproj +++ b/src/Microsoft.NuGet.Build.Tasks.Tests/Microsoft.NuGet.Build.Tasks.Tests.csproj @@ -85,6 +85,7 @@ + diff --git a/src/Microsoft.NuGet.Build.Tasks.Tests/ReferenceResolutionTests.cs b/src/Microsoft.NuGet.Build.Tasks.Tests/ReferenceResolutionTests.cs index 828a72b..994fdb4 100644 --- a/src/Microsoft.NuGet.Build.Tasks.Tests/ReferenceResolutionTests.cs +++ b/src/Microsoft.NuGet.Build.Tasks.Tests/ReferenceResolutionTests.cs @@ -413,5 +413,16 @@ namespace Microsoft.NuGet.Build.Tasks.Tests Assert.Contains("FluentAssertions", packageNames); } + + [Fact] + public static void ProjectsNotIncludedInReferences() + { + var result = NuGetTestHelpers.ResolvePackagesWithJsonFileContents( + Json.Json.ProjectDependency, + targetMoniker: ".NETFramework,Version=v4.5.2", + runtimeIdentifier: "win"); + + Assert.DoesNotContain("ClassLibrary1", result.ReferencedPackages.Select(t => t.ItemSpec)); + } } } diff --git a/src/Microsoft.NuGet.Build.Tasks/Microsoft.NuGet.Build.Tasks.csproj b/src/Microsoft.NuGet.Build.Tasks/Microsoft.NuGet.Build.Tasks.csproj index 8aba143..3d8611b 100644 --- a/src/Microsoft.NuGet.Build.Tasks/Microsoft.NuGet.Build.Tasks.csproj +++ b/src/Microsoft.NuGet.Build.Tasks/Microsoft.NuGet.Build.Tasks.csproj @@ -80,4 +80,4 @@ --> - + \ No newline at end of file diff --git a/src/Microsoft.NuGet.Build.Tasks/ResolveNuGetPackageAssets.cs b/src/Microsoft.NuGet.Build.Tasks/ResolveNuGetPackageAssets.cs index 3e12fb0..68ee462 100644 --- a/src/Microsoft.NuGet.Build.Tasks/ResolveNuGetPackageAssets.cs +++ b/src/Microsoft.NuGet.Build.Tasks/ResolveNuGetPackageAssets.cs @@ -854,24 +854,54 @@ namespace Microsoft.NuGet.Build.Tasks } var projectFileDependencyGroups = (JObject)lockFile["projectFileDependencyGroups"]; + var allPackageNames = GetAllPackageNames(lockFile); if (targetMoniker != null) { var targetSpecificDependencies = (JArray)projectFileDependencyGroups[targetMoniker]; if (targetSpecificDependencies != null) { - AddReferencedPackages(targetSpecificDependencies); + AddReferencedPackages(targetSpecificDependencies, allPackageNames); } } var universalDependencies = (JArray)projectFileDependencyGroups[""]; if (universalDependencies != null) { - AddReferencedPackages(universalDependencies); + AddReferencedPackages(universalDependencies, allPackageNames); } } - private void AddReferencedPackages(JArray packageDependencies) + /// + /// Returns the set of all the package names (not including version numbers) + /// in the "libraries" section of the assets/lock file. Note that this includes + /// only proper packages; projects are specifically excluded. + /// + private static SortedSet GetAllPackageNames(JObject lockFile) + { + var allPackageNames = new SortedSet(); + var libraries = (JObject)lockFile["libraries"]; + foreach (var library in libraries) + { + var libraryObject = (JObject)library.Value; + string type = (string)libraryObject["type"]; + if (type != null && + type.Equals("project", StringComparison.OrdinalIgnoreCase)) + { + continue; + } + + SplitPackageName(library.Key, out string name, out string version); + allPackageNames.Add(name); + } + + return allPackageNames; + } + + /// + /// Given a set of dependencies, identities the packages and adds their names to . + /// + private void AddReferencedPackages(JArray packageDependencies, SortedSet allPackageNames) { foreach (var packageDependency in packageDependencies.Select(v => (string)v)) { @@ -881,7 +911,10 @@ namespace Microsoft.NuGet.Build.Tasks ? packageDependency.Substring(0, firstSpace) : packageDependency; - _referencedPackages.Add(new TaskItem(packageName)); + if (allPackageNames.Contains(packageName)) + { + _referencedPackages.Add(new TaskItem(packageName)); + } } } @@ -906,9 +939,7 @@ namespace Microsoft.NuGet.Build.Tasks { foreach (var package in target) { - var nameParts = package.Key.Split('/'); - var id = nameParts[0]; - var version = nameParts[1]; + SplitPackageName(package.Key, out string id, out string version); var libraryObject = (JObject)lockFile["libraries"][package.Key]; @@ -933,6 +964,13 @@ namespace Microsoft.NuGet.Build.Tasks } } + private static void SplitPackageName(string key, out string id, out string version) + { + var nameParts = key.Split('/'); + id = nameParts[0]; + version = nameParts[1]; + } + private string GetAbsolutePathFromProjectRelativePath(string path) { return Path.GetFullPath(Path.Combine(Path.GetDirectoryName(Path.GetFullPath(ProjectLockFile)), path)); -- cgit v1.2.3 From 112685a925e5c0d26fcf9c9006341d4fa4f66515 Mon Sep 17 00:00:00 2001 From: Ankit Jain Date: Thu, 10 Aug 2017 18:04:27 -0400 Subject: Fix finding packages in lower-case dirs on case-sensitive .. .. filesystems. NuGet now restores packages in lower case directory names, but the build task `ResolveNuGetPackageAssets` constructs the path from package name and version, like: `Microsoft.NETCore.Portable.Compatibility/1.0.1` .. instead of `microsoft.netcore.portable.compatibility/1.0.1` This breaks builds on msbuild/mono on case-sensitive filesystems, eg. on Linux. The actual on-disk path is available in the lock/assets.json file as: ``` "libraries": { "Newtonsoft.Json/10.0.2": { ... "path": "newtonsoft.json/10.0.2", ... ``` So, we use that to look for the package. But fallback to the old method if this `"path"` is not available. --- .../NuGetPackageObject.cs | 1 + .../ResolveNuGetPackageAssets.cs | 28 +++++++++++++--------- 2 files changed, 18 insertions(+), 11 deletions(-) diff --git a/src/Microsoft.NuGet.Build.Tasks/NuGetPackageObject.cs b/src/Microsoft.NuGet.Build.Tasks/NuGetPackageObject.cs index 696db15..b4add3c 100644 --- a/src/Microsoft.NuGet.Build.Tasks/NuGetPackageObject.cs +++ b/src/Microsoft.NuGet.Build.Tasks/NuGetPackageObject.cs @@ -34,6 +34,7 @@ namespace Microsoft.NuGet.Build.Tasks public string Id { get; } public string Version { get; } + public string RelativePackagePath => (string)LibraryObject["path"]; /// /// The JSON object from the "targets" section in the project.lock.json for this package. diff --git a/src/Microsoft.NuGet.Build.Tasks/ResolveNuGetPackageAssets.cs b/src/Microsoft.NuGet.Build.Tasks/ResolveNuGetPackageAssets.cs index 68ee462..f4a7f17 100644 --- a/src/Microsoft.NuGet.Build.Tasks/ResolveNuGetPackageAssets.cs +++ b/src/Microsoft.NuGet.Build.Tasks/ResolveNuGetPackageAssets.cs @@ -369,7 +369,7 @@ namespace Microsoft.NuGet.Build.Tasks if (Path.GetExtension(file).Equals(".dll", StringComparison.OrdinalIgnoreCase)) { string path; - if (TryGetFile(package.Id, package.Version, file, out path)) + if (TryGetFile(package.Id, package.Version, package.RelativePackagePath, file, out path)) { var analyzer = new TaskItem(path); @@ -441,16 +441,16 @@ namespace Microsoft.NuGet.Build.Tasks } } - private bool TryGetFile(string packageName, string packageVersion, string file, out string path) + private bool TryGetFile(string packageName, string packageVersion, string packageRelativePath, string file, out string path) { if (IsFileValid(file, "C#", "VB")) { - path = GetPath(packageName, packageVersion, file); + path = GetPath(packageName, packageVersion, packageRelativePath, file); return true; } else if (IsFileValid(file, "VB", "C#")) { - path = GetPath(packageName, packageVersion, file); + path = GetPath(packageName, packageVersion, packageRelativePath, file); return true; } @@ -469,9 +469,9 @@ namespace Microsoft.NuGet.Build.Tasks !file.Split('/').Any(x => x.Equals(unExpectedLanguage, StringComparison.OrdinalIgnoreCase))); } - private string GetPath(string packageName, string packageVersion, string file) + private string GetPath(string packageName, string packageVersion, string packageRelativePath, string file) { - return Path.Combine(GetNuGetPackagePath(packageName, packageVersion), file.Replace('/', '\\')); + return Path.Combine(GetNuGetPackagePath(packageName, packageVersion, packageRelativePath), file.Replace('/', '\\')); } /// @@ -918,17 +918,23 @@ namespace Microsoft.NuGet.Build.Tasks } } - private string GetNuGetPackagePath(string packageId, string packageVersion) + private string GetNuGetPackagePath(string packageId, string packageVersion, string packageRelativePath) { + string relativePathToUse = String.IsNullOrEmpty(packageRelativePath) + ? Path.Combine(packageId, packageVersion) + : packageRelativePath.Replace('/', Path.DirectorySeparatorChar); + + string hashFileName = $"{packageId.ToLowerInvariant()}.{packageVersion.ToLowerInvariant()}.nupkg.sha512"; + foreach (var packagesFolder in _packageFolders) { - string packagePath = Path.Combine(packagesFolder, packageId, packageVersion); + string packageFullPath = Path.Combine(packagesFolder, relativePathToUse); // The proper way to check if a package is available is to look for the hash file, since that's the last // file written as a part of the restore process. If it's not there, it means something failed part way through. - if (_fileExists(Path.Combine(packagePath, $"{packageId}.{packageVersion}.nupkg.sha512"))) + if (_fileExists(Path.Combine(packageFullPath, hashFileName))) { - return packagePath; + return packageFullPath; } } @@ -957,7 +963,7 @@ namespace Microsoft.NuGet.Build.Tasks } else { - fullPackagePathGenerator = () => GetNuGetPackagePath(id, version); + fullPackagePathGenerator = () => GetNuGetPackagePath(id, version, (string)libraryObject["path"]); } yield return new NuGetPackageObject(id, version, fullPackagePathGenerator, (JObject)package.Value, libraryObject); -- cgit v1.2.3 From b279041f6a06b8c8df174625b07b833ae7862f20 Mon Sep 17 00:00:00 2001 From: Nat Ayewah Date: Wed, 6 Sep 2017 19:02:00 -0700 Subject: Fix failing test due to changed casing because task uses the casing in the assets file following #35 --- src/Microsoft.NuGet.Build.Tasks.Tests/PackageFolderTests.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Microsoft.NuGet.Build.Tasks.Tests/PackageFolderTests.cs b/src/Microsoft.NuGet.Build.Tasks.Tests/PackageFolderTests.cs index d8ef819..145e469 100644 --- a/src/Microsoft.NuGet.Build.Tasks.Tests/PackageFolderTests.cs +++ b/src/Microsoft.NuGet.Build.Tasks.Tests/PackageFolderTests.cs @@ -18,7 +18,7 @@ namespace Microsoft.NuGet.Build.Tasks.Tests runtimeIdentifier: null, createTemporaryFolderForPackages: false); - Assert.Equal(@"C:\PackageFolder\Newtonsoft.Json\8.0.3\lib\net45\Newtonsoft.Json.dll", result.References.Single().ItemSpec); + Assert.Equal(@"C:\PackageFolder\newtonsoft.json\8.0.3\lib\net45\Newtonsoft.Json.dll", result.References.Single().ItemSpec); } } } -- cgit v1.2.3