我有一个非常奇怪的情况,当从Windows Server 2012 R2手动运行时,同一命令可以正常工作,但不能从同一服务器上运行的Jenkins从属进程运行。
首先,手动运行的输出,一个管理PowerShell窗口:
PS C:\Users\Administrator> whoami
win-cm8utd1qfnc\administrator
PS C:\Users\Administrator> Invoke-Command -computername web.sandbox.MUNGED.com -scriptblock {iisreset /restart}
Attempting stop...
Internet services successfully stopped
Attempting start...
Internet services successfully restarted
大。现在,Jenkins管道代码的相关片段:
pipeline {
stages {
stage('Deploy web') {
agent { label 'windows-server-2012' }
environment {
SERVER = 'web.sandbox.MUNGED.com'
}
steps {
powershell """
whoami
Invoke-Command -computername ${SERVER} -scriptblock {iisreset /restart}
"""
}
}
}
}
从Jenkins运行时的输出:
07:37:29 win-cm8utd1qfnc\administrator
07:37:29 [web.sandbox.MUNGED.com] Connecting to remote server web.sandbox.MUNGED.com failed with the following error message : Access is denied. For more information, see the
07:37:29 about_Remote_Troubleshooting Help topic.
07:37:29 + CategoryInfo : OpenError: (web.sandbox.MUNGED.com:String) [], PSRemotingTransportException
07:37:29 + FullyQualifiedErrorId : AccessDenied,PSSessionStateBroken
Windows服务器(Jenkins从属服务器和Web服务器)不属于域,但具有相同的管理员密码,这似乎可以使身份验证工作正常。
对于它的价值,这里是Jenkins奴隶的winrm配置:
PS C:\Users\Administrator> winrm get winrm/config
Config
MaxEnvelopeSizekb = 500
MaxTimeoutms = 1800000
MaxBatchItems = 32000
MaxProviderRequests = 4294967295
Client
NetworkDelayms = 5000
URLPrefix = wsman
AllowUnencrypted = false
Auth
Basic = true
Digest = true
Kerberos = true
Negotiate = true
Certificate = true
CredSSP = false
DefaultPorts
HTTP = 5985
HTTPS = 5986
TrustedHosts = *
Service
RootSDDL = O:NSG:BAD:P(A;;GA;;;BA)(A;;GR;;;IU)S:P(AU;FA;GA;;;WD)(AU;SA;GXGW;;;WD)
MaxConcurrentOperations = 4294967295
MaxConcurrentOperationsPerUser = 1500
EnumerationTimeoutms = 240000
MaxConnections = 300
MaxPacketRetrievalTimeSeconds = 120
AllowUnencrypted = true
Auth
Basic = true
Kerberos = true
Negotiate = true
Certificate = false
CredSSP = false
CbtHardeningLevel = Relaxed
DefaultPorts
HTTP = 5985
HTTPS = 5986
IPv4Filter = *
IPv6Filter = *
EnableCompatibilityHttpListener = false
EnableCompatibilityHttpsListener = false
CertificateThumbprint
AllowRemoteAccess = true
Winrs
AllowRemoteShellAccess = true
IdleTimeout = 7200000
MaxConcurrentUsers = 10
MaxShellRunTime = 2147483647
MaxProcessesPerShell = 4096
MaxMemoryPerShellMB = 8192
MaxShellsPerUser = 30
来自网络服务器:
PS C:\Users\Administrator> winrm get winrm/config
Config
MaxEnvelopeSizekb = 500
MaxTimeoutms = 1800000
MaxBatchItems = 32000
MaxProviderRequests = 4294967295
Client
NetworkDelayms = 5000
URLPrefix = wsman
AllowUnencrypted = false
Auth
Basic = true
Digest = true
Kerberos = true
Negotiate = true
Certificate = true
CredSSP = false
DefaultPorts
HTTP = 5985
HTTPS = 5986
TrustedHosts = *
Service
RootSDDL = O:NSG:BAD:P(A;;GA;;;BA)(A;;GR;;;IU)S:P(AU;FA;GA;;;WD)(AU;SA;GXGW;;;WD)
MaxConcurrentOperations = 4294967295
MaxConcurrentOperationsPerUser = 1500
EnumerationTimeoutms = 240000
MaxConnections = 300
MaxPacketRetrievalTimeSeconds = 120
AllowUnencrypted = true
Auth
Basic = true
Kerberos = true
Negotiate = true
Certificate = false
CredSSP = false
CbtHardeningLevel = Relaxed
DefaultPorts
HTTP = 5985
HTTPS = 5986
IPv4Filter = *
IPv6Filter = *
EnableCompatibilityHttpListener = false
EnableCompatibilityHttpsListener = false
CertificateThumbprint
AllowRemoteAccess = true
Winrs
AllowRemoteShellAccess = true
IdleTimeout = 7200000
MaxConcurrentUsers = 10
MaxShellRunTime = 2147483647
MaxProcessesPerShell = 25
MaxMemoryPerShellMB = 1024
MaxShellsPerUser = 30
编辑:我在时尚之后开始工作了。首先,在詹金斯的奴隶上,我不得不跑:
winrm set winrm/config/client '@{AllowUnencrypted="true"}'
然后我将管道更改为:
powershell """
\$creds = Import-CliXml \$home\\creds.xml
Invoke-Command -computername ${SERVER} -scriptblock {iisreset /restart} -Authentication Basic -Credential \$creds
"""
其中creds.xml
是先前使用Get-Credentials | Export-CliXml creds.xml
生成的文件。
这仍然无法解释为什么手动PowerShell和Jenkins slave之间的行为有所不同。这有点令人讨厌,但至少我可以继续。
答案 0 :(得分:0)
你可能正在从Jenkins遇到远程执行脚本限制(安全性是这里的原因)。您需要将Jenkins服务器配置为能够运行脚本"通常"但是你总是要添加凭证。
您从powershell命令行运行的脚本使用win-cm8utd1qfnc\administrator
的默认凭据,因此以下内容将按您的说法运行:
PS C:\Users\Administrator> whoami
win-cm8utd1qfnc\administrator
PS C:\Users\Administrator> Invoke-Command -computername web.sandbox.MUNGED.com -scriptblock {iisreset /restart}
Attempting stop...
Internet services successfully stopped
Attempting start...
Internet services successfully restarted
然而,当从Jenkins运行Powershell时,就其性质而言,你正在达到设计安全性的限制。你不想跑#34;狂野"管理帐户的脚本。
我在这个主题上找到的最合理的指南是here(以下摘录自页面:
他上面的工作在Jenkins服务器上创建了一个文本文件。至 设置远程Powershell脚本我们首先需要配置Jenkins 用于远程Powershell脚本执行的服务器。启用远程 Windows机器进入Jenkins服务器上的WS-Man可信列表。 在Jenkins服务器上的Powershell窗口上执行以下命令。该 命令会将所有远程计算机添加到可信列表中。
Set-Item WSMan:\localhost\Client\TrustedHosts *
除了命令之外,我们还需要启用远程脚本 执行也。启用远程执行Powershell脚本 在Jenkins服务器的Powershell窗口中执行以下命令。
Set-ExecutionPolicy RemoteSigned –Force
我们必须安装一个名为EnvInject Plugin的新插件 转移变量例如密码。
Login to Jenkins and navigate to Manage Jenkins > Manage Plugins Click on the Available tab and Enter EnvInject in the filter box Select the plugin showing by name PowerShell Plugin Select Download now and install after restart
创建作业以重新启动Windows时间服务:
On Jenkins interface, click New Item Enter Remote Powershell scripts for the job name. Select Freestyle project Tick This build is parameterized. Create following parameters Type: String Parameter Name: ServerIp/Hostname Description: Remote machine’s IP address. Type: String Parameter Name: UserName Type: Password Parameter Name: Password Now, Click Add Parameter list and select the Choice Parameter. Enter the options on new lines inside the Choices text box. Also,
提供所提及选项的说明:
以下脚本基于上面的链接,但我不喜欢使用的纯文本,因此我决定将其重写为使用Powershell SecureString
首先存储您的管理员密码:
read-host -AsSecureString | ConvertFrom-SecureString | Out-File C:\<your_path>\securestring.txt
然后有脚本:
# Configure build failure on errors on the remote machine similar to set -x on bash script
$ErrorActionPreference = 'Stop'
# Create a PSCredential Object using the "Username" and "Password" variables created on job
$password = Get-Content 'C:\<your_path>\securestring.txt' | ConvertTo-SecureString
$creddentials = New-Object System.Management.Automation.PSCredential -ArgumentList $env:UserName, $password
# It depends on the type of job you are executing on the remote machine as to if you want to use "-ErrorAction Stop" on your Invoke-Command.
Invoke-Command -ComputerName $env:Computer -Credential $credentials -ScriptBlock { Restart-Service -Name W32Time }
答案 1 :(得分:0)
看到这个问题:Remote Access with Powershell and Jenkins
需要将服务用户从本地系统更改为管理员。