Add PowerShell support to SSHRun

This commit adds PowerShell support to SSHRun.  It also changes the
default behavior of Windows shells to not allocate a TTY by default.
This commit is contained in:
Jeff Bonhag 2019-12-18 12:58:38 -05:00
parent e95c59542a
commit 2dc3a38067
No known key found for this signature in database
GPG Key ID: 32966F3FB5AC1129
2 changed files with 40 additions and 16 deletions

View File

@ -47,7 +47,10 @@ module Vagrant
# Add an extra space to the command so cmd.exe quoting works # Add an extra space to the command so cmd.exe quoting works
# properly # properly
command = "#{shell} /C #{command} " command = "#{shell} /C #{command} "
env[:tty] = false elsif shell == "powershell"
command = "$ProgressPreference = \"SilentlyContinue\"; #{command}"
command = Base64.strict_encode64(command.encode("UTF-16LE", "UTF-8"))
command = "#{shell} -encodedCommand #{command}"
else else
command = "#{shell} -c '#{command}'" command = "#{shell} -c '#{command}'"
end end
@ -57,10 +60,11 @@ module Vagrant
opts[:extra_args] ||= [] opts[:extra_args] ||= []
# Allow the user to specify a tty or non-tty manually, but if they # Allow the user to specify a tty or non-tty manually, but if they
# don't then we default to a TTY # don't then we default to a TTY unless they are using WinSSH
if !opts[:extra_args].include?("-t") && if !opts[:extra_args].include?("-t") &&
!opts[:extra_args].include?("-T") && !opts[:extra_args].include?("-T") &&
env[:tty] env[:tty] &&
env[:machine].config.vm.communicator != :winssh
opts[:extra_args] << "-t" opts[:extra_args] << "-t"
end end

View File

@ -93,11 +93,12 @@ describe Vagrant::Action::Builtin::SSHRun do
before do before do
expect(vm).to receive(:communicator).and_return(:winssh) expect(vm).to receive(:communicator).and_return(:winssh)
expect(config).to receive(:winssh).and_return(winssh) expect(config).to receive(:winssh).and_return(winssh)
env[:tty] = nil
end end
it "should use the WinSSH shell for running ssh commands" do it "should use the WinSSH shell for running ssh commands" do
ssh_info = { foo: :bar } ssh_info = { foo: :bar }
opts = {:extra_args=>["-t", "foo -c 'dir'"], :subprocess=>true} opts = {:extra_args=>["foo -c 'dir'"], :subprocess=>true}
expect(ssh_klass).to receive(:exec). expect(ssh_klass).to receive(:exec).
with(ssh_info, opts) with(ssh_info, opts)
@ -106,11 +107,10 @@ describe Vagrant::Action::Builtin::SSHRun do
env[:ssh_run_command] = "dir" env[:ssh_run_command] = "dir"
described_class.new(app, env).call(env) described_class.new(app, env).call(env)
end end
end
context "when shell is cmd" do context "when shell is cmd" do
before do before do
expect(ssh).to receive(:shell).and_return('cmd') expect(winssh).to receive(:shell).and_return('cmd')
end end
it "should use appropriate options for cmd" do it "should use appropriate options for cmd" do
@ -125,4 +125,24 @@ describe Vagrant::Action::Builtin::SSHRun do
described_class.new(app, env).call(env) described_class.new(app, env).call(env)
end end
end end
context "when shell is powershell" do
before do
expect(winssh).to receive(:shell).and_return('powershell')
end
it "should base64 encode the command" do
ssh_info = { foo: :bar }
encoded_command = "JABQAHIAbwBnAHIAZQBzAHMAUAByAGUAZgBlAHIAZQBuAGMAZQAgAD0AIAAiAFMAaQBsAGUAbgB0AGwAeQBDAG8AbgB0AGkAbgB1AGUAIgA7ACAAZABpAHIA"
opts = {:extra_args=>["powershell -encodedCommand #{encoded_command}"], :subprocess=>true}
expect(ssh_klass).to receive(:exec).
with(ssh_info, opts)
env[:ssh_info] = ssh_info
env[:ssh_run_command] = "dir"
described_class.new(app, env).call(env)
end
end
end
end end