Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
42 changes: 24 additions & 18 deletions src/code/PublishPSResource.cs
Original file line number Diff line number Diff line change
Expand Up @@ -780,8 +780,8 @@ private Hashtable ParseRequiredModules(Hashtable parsedMetadataHash)
if (!parsedMetadataHash.ContainsKey("requiredmodules"))
{
return null;
}
var requiredModules = parsedMetadataHash["requiredmodules"];
}
LanguagePrimitives.TryConvertTo<object[]>(parsedMetadataHash["requiredmodules"], out object[] requiredModules);

// Required modules can be:
// a. An array of hash tables of module name and version
Expand All @@ -790,23 +790,29 @@ private Hashtable ParseRequiredModules(Hashtable parsedMetadataHash)
// d. A single string module name

var dependenciesHash = new Hashtable();
if (LanguagePrimitives.TryConvertTo<Hashtable[]>(requiredModules, out Hashtable[] moduleList))
foreach (var reqModule in requiredModules)
{
// instead of returning an array of hashtables,
// loop through the array and add each element of
foreach (Hashtable hash in moduleList)
if (LanguagePrimitives.TryConvertTo<Hashtable>(reqModule, out Hashtable moduleHash))
{
dependenciesHash.Add(hash["ModuleName"], hash["ModuleVersion"]);
string moduleName = moduleHash["ModuleName"] as string;

if (moduleHash.ContainsKey("ModuleVersion"))
{
dependenciesHash.Add(moduleName, moduleHash["ModuleVersion"]);
}
else if (moduleHash.ContainsKey("RequiredVersion"))
{
dependenciesHash.Add(moduleName, moduleHash["RequiredVersion"]);
}
else {
dependenciesHash.Add(moduleName, string.Empty);
}
}
}
else if (LanguagePrimitives.TryConvertTo<string[]>(requiredModules, out string[] moduleNames))
{
foreach (var modName in moduleNames)
else if (LanguagePrimitives.TryConvertTo<string>(reqModule, out string moduleName))
{
dependenciesHash.Add(modName, string.Empty);
dependenciesHash.Add(moduleName, string.Empty);
}
}

var externalModuleDeps = parsedMetadataHash.ContainsKey("ExternalModuleDependencies") ?
parsedMetadataHash["ExternalModuleDependencies"] : null;

Expand All @@ -829,12 +835,12 @@ private bool CheckDependenciesExist(Hashtable dependencies, string repositoryNam
// Check to see that all dependencies are in the repository
// Searches for each dependency in the repository the pkg is being pushed to,
// If the dependency is not there, error
foreach (var dependency in dependencies.Keys)
foreach (DictionaryEntry dependency in dependencies)
{
// Need to make individual calls since we're look for exact version numbers or ranges.
var depName = new[] { (string)dependency };
var depName = dependency.Key as string;
// test version
string depVersion = dependencies[dependency] as string;
string depVersion = dependencies[depName] as string;
depVersion = string.IsNullOrWhiteSpace(depVersion) ? "*" : depVersion;

if (!Utils.TryGetVersionType(
Expand All @@ -857,11 +863,11 @@ private bool CheckDependenciesExist(Hashtable dependencies, string repositoryNam
var repository = new[] { repositoryName };
// Note: we set prerelease argument for FindByResourceName() to true because if no version is specified we want latest version (including prerelease).
// If version is specified it will get that one. There is also no way to specify a prerelease flag with RequiredModules hashtable of dependency so always try to get latest version.
var dependencyFound = findHelper.FindByResourceName(depName, ResourceType.Module, versionRange, nugetVersion, versionType, depVersion, prerelease: true, tag: null, repository, includeDependencies: false);
var dependencyFound = findHelper.FindByResourceName(new string[] { depName }, ResourceType.Module, versionRange, nugetVersion, versionType, depVersion, prerelease: true, tag: null, repository, includeDependencies: false);
if (dependencyFound == null || !dependencyFound.Any())
{
WriteError(new ErrorRecord(
new ArgumentException($"Dependency '{depName.First()}' was not found in repository '{repositoryName}'. Make sure the dependency is published to the repository before publishing this module."),
new ArgumentException($"Dependency '{depName}' was not found in repository '{repositoryName}'. Make sure the dependency is published to the repository before publishing this module."),
"DependencyNotFound",
ErrorCategory.ObjectNotFound,
this));
Expand Down
37 changes: 36 additions & 1 deletion test/PublishPSResourceTests/PublishPSResource.Tests.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -543,7 +543,7 @@ Describe "Test Publish-PSResource" -tags 'CI' {
(Get-ChildItem $script:repositoryPath).FullName | Should -Be $expectedPath
}

It "should publish a script with sExternalModuleDependencies that are not published" {
It "should publish a script with ExternalModuleDependencies that are not published" {
$scriptName = "test"
$scriptVersion = "1.0.0"
$scriptPath = Join-Path -Path $script:testScriptsFolderPath -ChildPath "$scriptName.ps1"
Expand Down Expand Up @@ -671,4 +671,39 @@ Describe "Test Publish-PSResource" -tags 'CI' {
$expectedPath = Join-Path -Path $script:repositoryPath2 -ChildPath "$ParentModuleName.$ParentVersion.nupkg"
(Get-ChildItem $script:repositoryPath2).FullName | Should -Contain $expectedPath
}

It "Publish a module with required modules (both in string format and hashtable format)" {
# look at functions in test utils for creating a module with prerelease
$ModuleName = "ParentModule"
$ModuleVersion = "1.0.0"
$ModuleRoot = Join-Path -Path $script:PublishModuleBase -ChildPath $ModuleName
New-Item $ModuleRoot -ItemType Directory
$ModuleManifestPath = Join-Path -Path $ModuleRoot -ChildPath "$ModuleName.psd1"

$ReqModule1Name = "ReqModule1"
$ReqModule1Version = "3.0.0"
$ReqModule1Root = Join-Path -Path $script:PublishModuleBase -ChildPath $ReqModule1Name
New-Item $ReqModule1Root -ItemType Directory
$ReqModule1ManifestPath = Join-Path -Path $ReqModule1Root -ChildPath "$ReqModule1Name.psd1"

$ReqModule2Name = "ReqModule2"
$ReqModule2Root = Join-Path -Path $script:PublishModuleBase -ChildPath $ReqModule2Name
New-Item $ReqModule2Root -ItemType Directory
$ReqModule2ManifestPath = Join-Path -Path $reqModule2Root -ChildPath "$ReqModule2Name.psd1"

New-ModuleManifest -Path $ModuleManifestPath -ModuleVersion $ModuleVersion -Description "$ModuleName module" -RequiredModules @( @{ "ModuleName" = $ReqModule1Name; "ModuleVersion" = $ReqModule1Version }, $ReqModule2Name )
New-ModuleManifest -Path $ReqModule1ManifestPath -ModuleVersion $ReqModule1Version -Description "$ReqModule1Name module"
New-ModuleManifest -Path $ReqModule2ManifestPath -Description "$ReqModule1Name module"

Publish-PSResource -Path $ReqModule1ManifestPath -Repository $testRepository2
Publish-PSResource -Path $ReqModule2ManifestPath -Repository $testRepository2

Install-PSResource $ReqModule1Name -Repository $testRepository2 -TrustRepository
Install-PSResource $ReqModule2Name -Repository $testRepository2 -TrustRepository

Publish-PSResource -Path $ModuleManifestPath -Repository $testRepository2

$expectedPath = Join-Path -Path $script:repositoryPath2 -ChildPath "$ModuleName.$ModuleVersion.nupkg"
(Get-ChildItem $script:repositoryPath2).FullName | Should -Contain $expectedPath
}
}