PSDependScripts/Package.ps1
<# .SYNOPSIS EXPERIMENTAL: Installs a package using the PackageManagement module .DESCRIPTION EXPERIMENTAL: Installs a package using the PackageManagement module Relevant Dependency metadata: Name: The name for this Package Version: Used to identify existing installs meeting this criteria, and as RequiredVersion for installation. Defaults to 'latest' Target: Used as 'Scope' for PowerShellGet provider, Destination for Nuget provider Source: Package source to use (Get-PackageSource, Register-PackageSource) Parameters: Every parameter you specify is splatted against Install-Package If you don't have the Nuget package provider, we install it for you .PARAMETER ProviderName Optionally specify the Provider name to use (Get-PackageProvider, Register-PackageProvider) .PARAMETER PSDependAction Test, Install, or Import the module. Defaults to Install Test: Return true or false on whether the dependency is in place Install: Install the dependency .EXAMPLE @{ jquery = @{ DependencyType = 'Package' Target = 'C:\MyProject' Source = 'nuget.org' } } # Install jquery from the nuget.org PackageSource to C:\MyProject # IMPORTANT: Only certain providers support specifying a target destination .EXAMPLE @{ jquery = @{ DependencyType = 'Package' Source = 'https://my.internal.nuget.feed/api' Target = 'C:\MyProject' Parameters = @{ ProviderName = 'nuget' } } } # Install jquery from my internal nuget feed to C:\MyProject #> [cmdletbinding()] param( [PSTypeName('PSDepend.Dependency')] [psobject[]]$Dependency, [ValidateSet('Test', 'Install')] [string[]]$PSDependAction = @('Install'), [String]$ProviderName ) # Extract data from Dependency $DependencyName = $Dependency.DependencyName $Source = $Dependency.Source $Name = $Dependency.Name if(-not $Name) { $Name = $DependencyName } $Version = $Dependency.Version if(-not $Version) { $Version = 'latest' } $PackageSources = @( Get-PackageSource ) if($PackageSources.Name -notcontains $Source -and -not $PSBoundParameters.ContainsKey('ProviderName')) { Write-Error "PackageSource [$Source] is not valid. Valid sources:`n$($PackageSources.ProviderName | Out-String)" return } $PackageProviders = @( Get-PackageProvider ) if($PSBoundParameters.ContainsKey('ProviderName') -and $PackageProviders.Name -notcontains $ProviderName) { Write-Error "ProviderName [$ProviderName] is not valid. Valid sources:`n$($PackageProviders.Name | Out-String)" return } Write-Verbose -Message "Getting dependency [$name] from Package source [$Source]" if($PSBoundParameters.ContainsKey('ProviderName')) { $ThisProvider = $ProviderName } else # Pick providername from this packagesource { $ThisProvider = $PackageSources | Where {$_.Name -eq $Source} | Select -ExpandProperty ProviderName } $GetParam = @{ Name = $Name ProviderName = $ThisProvider ErrorAction = 'SilentlyContinue' } $InstallParam = @{ Name = $Name Source = $Source Force = $True } if($Version -notlike 'latest') { $GetParam.add('RequiredVersion', $Version) $InstallParam.add('RequiredVersion', $Version) } # Parse target for PowerShellGet If($ThisProvider -eq 'PowerShellGet') { $ValidScope = 'CurrentUser', 'AllUsers' if(-not $Dependency.Target) { $Scope = 'AllUsers' $InstallParam.Add('Scope', $Scope) } elseif($ValidScope -contains $Scope) { $Scope = $Dependency.Target $InstallParam.Add('Scope', $Scope) } } # Parse target for Nuget if($ThisProvider -eq 'Nuget') { if(-not $Dependency.Target) { throw 'Nuget provider requires that you specify a target destination. Use the dependency Target for this.' } $GetParam.Add('Destination', $Dependency.Target) $InstallParam.Add('Destination', $Dependency.Target) } # Add arbitrary keys to support DynamicOptions... if($Dependency.Parameters.Keys.Count -gt 0) { foreach($Key in $Dependency.Parameters.Keys) { if(-not $InstallParam.ContainsKey($Key)) { $InstallParam.add($Key, $Dependency.Parameters.$Key) } else { $InstallParam.$Key = $Dependency.Parameters.$Key } } } $Existing = $null Write-Verbose "Running Get-Package with $($GetParam | Out-String)" $Existing = Get-Package @GetParam if($Existing) { Write-Verbose "Found existing package [$Name]" # Thanks to Brandon Padgett! $ExistingVersion = $Existing | Measure-Object -Property Version -Maximum | Select-Object -ExpandProperty Maximum $GetSourceVersion = { Find-Package -Name $Name -Source $Source | Measure-Object -Property Version -Maximum | Select-Object -ExpandProperty Maximum } # Version string, and equal to current if( $Version -and $Version -ne 'latest' -and $Version -eq $ExistingVersion) { Write-Verbose "You have the requested version [$Version] of [$Name]" if($PSDependAction -contains 'Test') { return $True } return $null } # latest, and we have latest if( $Version -and ($Version -eq 'latest' -or $Version -like '') -and ($SourceVersion = (& $GetSourceVersion)) -le $ExistingVersion ) { Write-Verbose "You have the latest version of [$Name], with installed version [$ExistingVersion] and package source version [$SourceVersion]" if($PSDependAction -contains 'Test') { return $True } return $null } Write-Verbose "Continuing to install [$Name]: Requested version [$version], existing version [$ExistingVersion]" } #No dependency found, return false if we're testing alone... if( $PSDependAction -contains 'Test' -and $PSDependAction.count -eq 1) { return $False } if($PSDependAction -contains 'Install') { Write-Verbose "Installing [$Name] with params $($InstallParam | Out-String)" Install-Package @InstallParam } |