Method: ChefMetalDocker::DockerTransport#execute

Defined in:
lib/chef_metal_docker/docker_transport.rb

#execute(command, options = {}) ⇒ Object

Execute the specified command inside the container, returns a Mixlib::Shellout object Options contains the optional keys:

:read_only => Do not commit this execute operation, just execute it
:ports => ports to listen on (-p command-line options)
:detached => true/false, execute this command in detached mode (for final program to run)


36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
# File 'lib/chef_metal_docker/docker_transport.rb', line 36

def execute(command, options={})
  Chef::Log.debug("execute '#{command}' with options #{options}")

  begin
    connection.post("/containers/#{container_name}/stop?t=0", '')
    Chef::Log.debug("stopped /containers/#{container_name}")
  rescue Excon::Errors::NotModified
    Chef::Log.debug("Already stopped #{container_name}")
  rescue Docker::Error::NotFoundError
  end

  begin
    # Delete the container if it exists and is dormant
    connection.delete("/containers/#{container_name}?v=true&force=true")
    Chef::Log.debug("deleted /containers/#{container_name}")
  rescue Docker::Error::NotFoundError
  end

  command = Shellwords.split(command) if command.is_a?(String)

  # TODO shell_out has no way to live stream stderr???
  live_stream = nil
  live_stream = STDOUT if options[:stream]
  live_stream = options[:stream_stdout] if options[:stream_stdout]

  args = ['docker', 'run', '--name', container_name]

  if options[:detached]
    args << '--detach'
  end

  if options[:ports]
    options[:ports].each do |portnum|
      args << '-p'
      args << "#{portnum}"
    end
  end

  if options[:keep_stdin_open]
    args << '-i'
  end

  args << @image.id
  args += command

  cmdstr = Shellwords.join(args)
  Chef::Log.debug("Executing #{cmdstr}")

  # Remove this when https://github.com/opscode/chef/pull/2100 gets merged and released
  # nullify live_stream because at the moment EventsOutputStream doesn't understand <<, which
  # ShellOut uses
  live_stream = nil unless live_stream.respond_to? :<<

  cmd = Mixlib::ShellOut.new(cmdstr, :live_stream => live_stream, :timeout => execute_timeout(options))

  cmd.run_command

  unless options[:read_only]
    Chef::Log.debug("Committing #{container_name} as #{repository_name}:#{container_name}")
    container = Docker::Container.get(container_name)
    @image = container.commit('repo' => repository_name, 'tag' => container_name)
  end

  Chef::Log.debug("Execute complete: status #{cmd.exitstatus}")

  cmd
end