diff --git a/src/code/FindHelper.cs b/src/code/FindHelper.cs index d8287c689..024623503 100644 --- a/src/code/FindHelper.cs +++ b/src/code/FindHelper.cs @@ -1171,6 +1171,70 @@ internal IEnumerable FindDependencyPackages( } } } + else if(dep.VersionRange.MaxVersion != null && dep.VersionRange.MinVersion != null && dep.VersionRange.MaxVersion.OriginalVersion.Equals(dep.VersionRange.MinVersion.OriginalVersion)) + { + string depPkgVersion = dep.VersionRange.MaxVersion.OriginalVersion; + FindResults responses = currentServer.FindVersion(dep.Name, version: dep.VersionRange.MaxVersion.OriginalVersion, _type, out ErrorRecord errRecord); + if (errRecord != null) + { + if (errRecord.Exception is ResourceNotFoundException) + { + _cmdletPassedIn.WriteVerbose(errRecord.Exception.Message); + } + else + { + _cmdletPassedIn.WriteError(errRecord); + } + yield return null; + continue; + } + + PSResourceResult currentResult = currentResponseUtil.ConvertToPSResourceResult(responses).FirstOrDefault(); + if (currentResult == null) + { + // This scenario may occur when the package version requested is unlisted. + _cmdletPassedIn.WriteError(new ErrorRecord( + new ResourceNotFoundException($"Dependency package with name '{dep.Name}' and version '{depPkgVersion}' could not be found in repository '{repository.Name}'"), + "DependencyPackageNotFound", + ErrorCategory.ObjectNotFound, + this)); + yield return null; + continue; + } + + if (currentResult.exception != null && !currentResult.exception.Message.Equals(string.Empty)) + { + _cmdletPassedIn.WriteError(new ErrorRecord( + new ResourceNotFoundException($"Dependency package with name '{dep.Name}' and version '{depPkgVersion}' could not be found in repository '{repository.Name}'", currentResult.exception), + "DependencyPackageNotFound", + ErrorCategory.ObjectNotFound, + this)); + yield return null; + continue; + } + + depPkg = currentResult.returnedObject; + + if (!_packagesFound.ContainsKey(depPkg.Name)) + { + foreach (PSResourceInfo depRes in FindDependencyPackages(currentServer, currentResponseUtil, depPkg, repository)) + { + yield return depRes; + } + } + else + { + List pkgVersions = _packagesFound[depPkg.Name] as List; + // _packagesFound has depPkg.name in it, but the version is not the same + if (!pkgVersions.Contains(FormatPkgVersionString(depPkg))) + { + foreach (PSResourceInfo depRes in FindDependencyPackages(currentServer, currentResponseUtil, depPkg, repository)) + { + yield return depRes; + } + } + } + } else { FindResults responses = currentServer.FindVersionGlobbing(dep.Name, dep.VersionRange, includePrerelease: true, ResourceType.None, getOnlyLatest: true, out ErrorRecord errRecord); diff --git a/src/code/FindPSResource.cs b/src/code/FindPSResource.cs index 2709073e7..a0ef9f496 100644 --- a/src/code/FindPSResource.cs +++ b/src/code/FindPSResource.cs @@ -234,6 +234,12 @@ private void ProcessResourceNameParameterSet() return; } + + if (versionRange.MinVersion != null && versionRange.MaxVersion != null && versionRange.MinVersion.OriginalVersion.Equals(versionRange.MaxVersion.OriginalVersion)) + { + nugetVersion = versionRange.MaxVersion; + versionType = VersionType.SpecificVersion; + } } else { diff --git a/test/FindPSResourceTests/FindPSResourceV2Server.Tests.ps1 b/test/FindPSResourceTests/FindPSResourceV2Server.Tests.ps1 index 139e68ab0..911471f3b 100644 --- a/test/FindPSResourceTests/FindPSResourceV2Server.Tests.ps1 +++ b/test/FindPSResourceTests/FindPSResourceV2Server.Tests.ps1 @@ -446,6 +446,17 @@ Describe 'Test HTTP Find-PSResource for V2 Server Protocol' -tags 'CI' { $res.Name | Should -Contain 'test_unlisted' $res.Name | Should -Contain 'test_notunlisted' } + + It "Find resource that takes a dependency on package with specific version" { + $moduleName = 'test-nugetversion-parent' + $version = '4.0.0' + $depPkgName = 'test-nugetversion' + + $res = Find-PSResource -Name $moduleName -Version $version -Repository $PSGalleryName -IncludeDependencies + $res.Count | Should -Be 2 + $res.Name | Should -Contain $moduleName + $res.Name | Should -Contain $depPkgName + } } Describe 'Test HTTP Find-PSResource for V2 Server Protocol' -tags 'ManualValidationOnly' { diff --git a/test/InstallPSResourceTests/InstallPSResourceV2Server.Tests.ps1 b/test/InstallPSResourceTests/InstallPSResourceV2Server.Tests.ps1 index e269b2628..852f5d3a3 100644 --- a/test/InstallPSResourceTests/InstallPSResourceV2Server.Tests.ps1 +++ b/test/InstallPSResourceTests/InstallPSResourceV2Server.Tests.ps1 @@ -32,7 +32,7 @@ Describe 'Test Install-PSResource for V2 Server scenarios' -tags 'CI' { AfterEach { Uninstall-PSResource "test_module", "test_module2", "test_script", "TestModule99", "testModuleWithlicense", ` "TestFindModule", "ClobberTestModule1", "ClobberTestModule2", "PackageManagement", "TestTestScript", ` - "TestModuleWithDependency", "TestModuleWithPrereleaseDep", "PrereleaseModule" -SkipDependencyCheck -ErrorAction SilentlyContinue + "TestModuleWithDependency", "TestModuleWithPrereleaseDep", "PrereleaseModule", "test-nugetversion-parent", "test-nugetversion" -SkipDependencyCheck -ErrorAction SilentlyContinue } AfterAll { @@ -616,6 +616,21 @@ Describe 'Test Install-PSResource for V2 Server scenarios' -tags 'CI' { $res | Should -Not -BeNullOrEmpty $res.Version | Should -Be $version } + + It "Install resource that takes a dependency on package with specific version" { + $moduleName = 'test-nugetversion-parent' + $version = '4.0.0' + $depPkgName = 'test-nugetversion' + $depPkgVer = '5.0.1' + + Install-PSResource -Name $moduleName -Version $version -Repository $PSGalleryName -TrustRepository + $res = Get-InstalledPSResource $moduleName + $res.Name | Should -Be $moduleName + $res.Version | Should -Be $version + $depRes = Get-InstalledPSResource $depPkgName + $depRes.Name | Should -Be $depPkgName + $depRes.Version | Should -Be $depPkgVer + } } Describe 'Test Install-PSResource for V2 Server scenarios' -tags 'ManualValidationOnly' {