1

是否可以仅通过定义新模块清单并将其放在指定目录中来注册新的 PowerShell 模块?

SampleModule例如,应该创建一个名为的新模块。我将空清单文件SampleModule.psd1放在目录中<%PSModulePath%>\SampleModule。(使用哪个(用户或全局)模块路径都没有关系)。

这足以让 PowerShell 使用该Get-Module -ListAvailable命令列出我的新模块。

在下一步中,我尝试填充清单并将ModuleToProcess属性设置为位于另一个目录中的程序集。调用Import-Module失败,PowerShell 找不到程序集。

4

2 回答 2

1

真的是。事实上,我有一个非常巧妙的技巧可以为 SQL 管理单元执行此操作。代码的第一块是一个函数,它将从一个模块位置为您创建一个模块清单。它仍然会提示您(就像 New-ModuleManifest cmdlet 一样)一些必需的参数,例如描述。它查找任何类型和格式文件,以及任何 .dll 的命名为.ps .dll(大多数管理单元都遵循此约定),然后它创建一个包装原始模块的模块清单。第二块代码专门针对 SQL PSSnapin 执行此操作。

function New-ModuleManifestFromSnapIn {

    [CmdletBinding(SupportsShouldProcess=$true, ConfirmImpact='Medium')]
    param(

    [Parameter(Mandatory=$true, Position=0)]
    [System.String]
    ${Path},

    # The location in the filesystem where the V1 snapin resides
    [Parameter(Mandatory=$true)]
    [System.String]
    ${OriginalPath},

    [System.Guid]
    ${Guid},

    [Parameter(Mandatory=$true)]
    [AllowEmptyString()]
    [System.String]
    ${Author},

    [Parameter(Mandatory=$true)]
    [AllowEmptyString()]
    [System.String]
    ${CompanyName},

    [Parameter(Mandatory=$true)]
    [AllowEmptyString()]
    [System.String]
    ${Copyright},

    [ValidateNotNull()]
    [System.Version]
    ${ModuleVersion},

    [Parameter(Mandatory=$true)]
    [AllowEmptyString()]
    [System.String]
    ${Description},

    [System.Reflection.ProcessorArchitecture]
    ${ProcessorArchitecture},

    [System.Version]
    ${PowerShellVersion},

    [System.Version]
    ${ClrVersion},

    [System.Version]
    ${DotNetFrameworkVersion},

    [System.String]
    ${PowerShellHostName},

    [System.Version]
    ${PowerShellHostVersion},

    [System.Object[]]
    ${RequiredModules},

    [AllowEmptyCollection()]
    [System.String[]]
    ${ScriptsToProcess},

    [AllowEmptyCollection()]
    [System.Object[]]
    ${ModuleList},

    [AllowNull()]
    [System.Object]
    ${PrivateData},

    [Switch]
    ${PassThru}
    )

    process {
        $types = Get-ChildItem $originalPath -Filter *.types.ps1xml
        $formats = Get-ChildItem $originalPath -Filter *.format.ps1xml
        $dlls = Get-ChildItem $originalPath -Filter *.ps*.dll
        $null = $psBoundParameters.Remove("OriginalPath")
        $psBoundParameters += @{
            VariablesToExport = "*"
            FunctionsToExport = "*"
            AliasesToExport = "*"
            CmdletsToExport = "*"
            FileList = @()
            RequiredAssemblies = @()
            ModuleToProcess = ""
            NestedModules = @($dlls | Select-Object -ExpandProperty FullName)
            TypesToProcess = @($types | Select-Object -ExpandProperty FullName)
            FormatsToProcess = @($formats | Select-Object -ExpandProperty FullName)
        }
        New-ModuleManifest @psBoundParameters
    }
}

此块将显示通过指向工具@SQL 创建清单。

$basePath = $env:SqlSamplesSourceDataPath | Split-Path
if (${env:ProgramFiles(x86)}) {
    $basePath = $basePath.Replace($env:ProgramFiles, ${env:ProgramFiles(x86)})
} 

$path = Join-Path $basePath "Binn"


$basicMetaData = @{
    Author = "Microsoft Corporation"
    Description = "A Manifest to enable using the SQL PowerShell snapin in V2"
    CompanyName = "Microsoft Corporation"
    Copyright = (Get-Date).Year 
}
New-ModuleManifestFromSnapin -Path $psScriptRoot\Sql.psd1 -OriginalPath $path @BasicMetaData

最后一个块会将任何名为当前区域性的文件(即 SQL\en-us)复制到模块目录中,这将使 Get-Help 对 cmdlet 起作用。

此技巧适用于一些管理单元,但可能需要对您希望作为模块重新公开的每个管理单元进行一些自定义。幸运的是,这是一次性成本。

$Culture = Get-Culture
$CultureList = "$path\$culture", 
    (Join-Path $path $culture.ThreeLetterIsoLanguageName), 
    (Join-Path $path $culture.TwoLetterIsoLanguageName)

$CultureDirectory = Get-Item $CultureList -ErrorAction SilentlyContinue |
    Select-Object -First 1 

if ($CultureDirectory) {
    $localDir = Join-Path $psScriptRoot (Split-Path $CultureDirectory -Leaf)
    $item = Get-Item $localDir -ErrorAction SilentlyContinue 
    if ($item) {
        Remove-Item $item -Recurse -Force 
    }
    Copy-Item $CultureDirectory $LocalDir -Recurse
}

希望这可以帮助

于 2010-01-22T22:07:18.120 回答
1

带有参数的Get-Modulecmdlet-ListAvailable效果很好。问题在于架构,即 32 位 PowerShell 主机无法列出 64 位模块...

于 2010-01-25T14:08:24.803 回答