Skip to content

Commit

Permalink
Test-ModuleExist: New public command (#121)
Browse files Browse the repository at this point in the history
  • Loading branch information
johlju authored Feb 13, 2024
1 parent cb72a3e commit 9471465
Show file tree
Hide file tree
Showing 4 changed files with 430 additions and 1 deletion.
3 changes: 3 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,9 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- Can now return the individual module path for different scopes when
using the parameter `-Scope`. If no parameter is specified the command
return the path for the scope CurrentUser.
- `Test-ModuleExist`
- Checks if a PowerShell module with a specified name is available in a
PSModulePath.

### Fixed

Expand Down
5 changes: 4 additions & 1 deletion source/Public/Assert-Module.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,10 @@
.DESCRIPTION
Assert if the specific module is available to be imported and optionally
import the module.
import the module. If the module is not available an exception will be
thrown.
See also `Test-ModuleExist`.
.PARAMETER ModuleName
Specifies the name of the module to assert.
Expand Down
141 changes: 141 additions & 0 deletions source/Public/Test-ModuleExist.ps1
Original file line number Diff line number Diff line change
@@ -0,0 +1,141 @@
<#
.SYNOPSIS
Checks if a PowerShell module with a specified name is available in a
`$env:PSModulePath`.
.DESCRIPTION
The Test-ModuleExist function checks if a PowerShell module with the specified
name is available in a `$env:PSModulePath`. It can also filter the modules based on
the scope or folder path. Additionally, it can filter the modules based on
a specific version.
See also `Assert-Module`.
.PARAMETER Name
The name of the module to check is available.
.PARAMETER Scope
The scope where the module should be available. This parameter is used to
filter the modules based on the scope.
.PARAMETER Path
The path where the module should be available. This parameter is used to
filter the modules based on the path. The specified path must match (fully
or partially) one of the `$env:PSModulePath` paths.
.PARAMETER Version
The version of the module. This parameter is used to filter the modules
based on a specific version.
.EXAMPLE
Test-ModuleExist -Name 'MyModule' -Scope 'CurrentUser'
Checks if a module named 'MyModule' exists in the current user's module scope.
.EXAMPLE
Test-ModuleExist -Name 'MyModule' -Path 'C:\Modules'
Checks if a module named 'MyModule' exists in the specified path.
.EXAMPLE
Test-ModuleExist -Name 'MyModule' -Path 'local/share/powershell/Module'
Checks if a module named 'MyModule' exists in a `$env:PSModulePath` that
matches the specified path. If for example 'MyModule' exist in the path
`/home/username/.local/share/powershell/Module` it returns `$true`.
.EXAMPLE
Test-ModuleExist -Name 'MyModule' -Version '1.0.0'
Checks if a module named 'MyModule' with version '1.0.0' exists.
.OUTPUTS
System.Boolean
#>

function Test-ModuleExist
{
[CmdletBinding(DefaultParameterSetName = 'Default')]
param
(
[Parameter(ParameterSetName = 'Default')]
[Parameter(ParameterSetName = 'Scope')]
[Parameter(ParameterSetName = 'Path')]
[Parameter(Mandatory = $true)]
[System.String]
$Name,

[Parameter(Mandatory = $true, ParameterSetName = 'Scope')]
[ValidateSet('CurrentUser', 'AllUsers')]
[System.String]
$Scope,

[Parameter(Mandatory = $true, ParameterSetName = 'Path')]
[System.String]
$Path,

[Parameter(ParameterSetName = 'Default')]
[Parameter(ParameterSetName = 'Scope')]
[Parameter(ParameterSetName = 'Path')]
[ValidateScript({
# From https://semver.org/#is-there-a-suggested-regular-expression-regex-to-check-a-semver-string
$_ -match '^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$'
})]
[System.String]
$Version
)

$availableModules = @(Get-Module -Name $Name -ListAvailable)

$modulePath = switch ($PSCmdlet.ParameterSetName)
{
'Scope'
{
Get-PSModulePath -Scope $Scope
}

'Path'
{
$Path
}
}

if ($modulePath)
{
Write-Verbose -Message "Filtering modules by path '$modulePath'."

$modulesToEvaluate = $availableModules |
Where-Object -FilterScript {
$_.Path -match [System.Text.RegularExpressions.Regex]::Escape($modulePath)
}
}
else
{
$modulesToEvaluate = $availableModules
}

if ($modulesToEvaluate -and $PSBoundParameters.Version)
{
$moduleVersion, $modulePrerelease = $Version -split '-'

Write-Verbose -Message "Filtering modules by version '$moduleVersion'."

$modulesToEvaluate = $modulesToEvaluate |
Where-Object -FilterScript {
$_.Version -eq $moduleVersion
}

if ($modulesToEvaluate -and $modulePrerelease)
{
Write-Verbose -Message "Filtering modules by prerelease '$modulePrerelease'."

$modulesToEvaluate = $modulesToEvaluate |
Where-Object -FilterScript {
$_.PrivateData.PSData.Prerelease -eq $modulePrerelease
}
}
}

return ($modulesToEvaluate -and $modulesToEvaluate.Count -gt 0)
}
Loading

0 comments on commit 9471465

Please sign in to comment.