我有这个代码,我在其中加载了一个snapin(在这种情况下来自MS Dynamics NAV):
using (Runspace runspace = RunspaceFactory.CreateRunspace())
{
runspace.Open();
using (var ps = PowerShell.Create())
{
ps.Runspace = runspace;
ps.AddScript("Add-PSSnapin Microsoft.Dynamics.Nav.Management")
.AddScript("Get-NAVServerInstance");
//This does not work. Says unknown cmdlet Get-NAVServerInstance
//ps.AddCommand("Add-PSSnapin").AddArgument("Microsoft.Dynamics.Nav.Management")
// .AddCommand("Get-NAVServerInstance");
var output = ps.Invoke();
}
}
当我使用代码中显示的AddScript方法时,此代码可以正常工作。 但是为什么AddCommand方法不起作用(参见注释代码)?看起来没有加载管理单元,因为错误表明Get-NAVServerInstance cmdlet未知。 这应该如何运作?
我知道我可以使用我已导入snapin的InitialSessionState创建一个运行空间。然后ps.AddCommand(“Get-NAVServerInstance”)正在运行。 但是当我想创建一个远程运行空间会话(使用WSManConnectionInfo)时,我找不到提供initialSessionState的方法。
更新: 因此,当运行空间被打开(或创建?)时,AddCommand似乎只能用于可用的cmdlet。使用带有RunspaceFactory.CreateRunspace(...)的InitialSessionState或RunspaceConfiguration实例可以。所以这段代码有效:
var config = RunspaceConfiguration.Create();
PSSnapInException warning;
config.AddPSSnapIn("Microsoft.Dynamics.Nav.Management", out warning);
using (Runspace runspace = RunspaceFactory.CreateRunspace(config))
{
runspace.Open();
using (var ps = PowerShell.Create())
{
ps.Runspace = runspace;
ps.AddCommand("Get-NAVServerInstance");
var output = ps.Invoke();
}
}
但我的问题是在那种情况下,我无法指定WSManConnectionInfo实例。
那么如何创建一个带有远程连接的运行空间,并且加载了一个snapin(安装在远程机器上)?如何为远程连接提供配置?
答案 0 :(得分:4)
我终于找到了如何配置远程会话的提示(参见https://superuser.com/a/518567)。
您需要使用
在远程计算机上注册会话配置Register-PSSessionConfiguration -Name MyShell -StartupScript 'MyInitScript.ps1'
然后,您可以将WSManConnectionInfo的shellUri参数设置为http://schemas.microsoft.com/powershell/MyShell
以这种方式创建的运行空间将具有MyInitScript.ps1启动脚本导入的可用命令。
所以现在这段代码将起作用:
string shell = "http://schemas.microsoft.com/powershell/MyShell";
var target = new Uri("https://myserver:port/wsman");
var secured = new SecureString();
foreach (char letter in "password")
{
secured.AppendChar(letter);
}
secured.MakeReadOnly();
var credential = new PSCredential("username", secured);
var connectionInfo = new WSManConnectionInfo(target, shell, credential);
using (Runspace runspace = RunspaceFactory.CreateRunspace(connectionInfo))
{
runspace.Open();
using (var ps = PowerShell.Create())
{
ps.Runspace = runspace;
ps.AddCommand("Get-NAVServerInstance");
var output = ps.Invoke();
}
}
答案 1 :(得分:0)
尝试像这样调用AddScript:
.AddScript("...", false)
这将在全局范围内执行命令,而不是新的本地范围。
我认为正确的方法是使用RunspaceConfiguration类。它有一个AddPSSnapin方法。