require 'spec_helper' describe Ridley::HostConnector::WinRM::Worker do subject { winrm_worker } let(:winrm_worker) { described_class.new(host, options) } let(:host) { 'reset.riotgames.com' } let(:options) { {} } before do Ridley::HostConnector::WinRM::CommandUploader.stub(:new).and_return(double('command_uploader')) end describe "#winrm_port" do subject(:winrm_port) { winrm_worker.winrm_port } it { should eq(Ridley::HostConnector::DEFAULT_WINRM_PORT) } context "when overridden" do let(:options) { { winrm: { port: 1234 } } } it { should eq(1234) } end end describe "#winrm" do subject { winrm_worker.winrm } it "returns a WinRM::WinRMWebService" do expect(subject).to be_a(::WinRM::WinRMWebService) end end describe "#get_command" do subject(:get_command) { winrm_worker.get_command(command, command_uploader_stub) } let(:command) { "echo %TEMP%" } let(:command_uploader_stub) { double('CommandUploader') } it { should eq(command) } context "when a command is more than 2047 characters" do let(:command) { "a" * 2048 } it "uploads and returns a command" do Ridley::HostConnector::WinRM::CommandUploader.stub new: command_uploader_stub command_uploader_stub.should_receive :upload command_uploader_stub.stub command: "my command" command_uploader_stub.stub(:cleanup) get_command.should eq("my command") end end end describe "#run" do subject(:run) { winrm_worker.run(command) } let(:command) { "dir" } let(:command_uploader_stub) { double('CommandUploader') } let(:stdout) { "stdout" } let(:stderr) { nil } let(:winrm_stub) { double } before do Ridley::HostConnector::WinRM::CommandUploader.stub(:new).and_return(command_uploader_stub) winrm_worker.stub(:winrm).and_return(winrm_stub) winrm_stub.stub(:run_cmd).and_yield(stdout, stderr).and_return({exitcode: 0}) end context "when the exit_code is 0" do it "returns an :ok with the response" do status, response = run expect(status).to eq(:ok) expect(response.stdout).to eq("stdout") end end context "when the exit_code is not 0" do let(:stderr) { "stderr" } before do winrm_stub.stub(:run_cmd).and_yield(stdout, stderr).and_return({exitcode: 1}) end it "returns an :error with the response" do status, response = run expect(status).to eq(:error) expect(response.stderr).to eq("stderr") end end context "when an error is raised" do let(:stderr) { "error" } before do winrm_stub.stub(:run_cmd).and_yield(stdout, stderr).and_raise("error") end it "returns an :error with the response" do status, response = run expect(status).to eq(:error) expect(response.stderr).to eq("error") end end end describe "#chef_client" do subject(:chef_client) { winrm_worker.chef_client } it "receives a command to run chef-client" do winrm_worker.should_receive(:run).with("chef-client") chef_client end end describe "#put_secret" do subject(:put_secret) { winrm_worker.put_secret(secret) } let(:encrypted_data_bag_secret_path) { fixtures_path.join("encrypted_data_bag_secret").to_s } let(:secret) { File.read(encrypted_data_bag_secret_path).chomp } it "receives a command to copy the secret" do winrm_worker.should_receive(:run).with("echo #{secret} > C:\\chef\\encrypted_data_bag_secret") put_secret end end describe "#ruby_script" do subject(:ruby_script) { winrm_worker.ruby_script(command_lines) } let(:command_lines) { ["puts 'hello'", "puts 'there'"] } it "receives a ruby call with the command" do winrm_worker.should_receive(:run).with("#{described_class::EMBEDDED_RUBY_PATH} -e \"puts 'hello';puts 'there'\"") ruby_script end end end