Class: Kitchen::Driver::SSHBase Deprecated

Inherits:
Object
  • Object
show all
Includes:
Configurable, Logging, ShellOut
Defined in:
lib/kitchen/driver/ssh_base.rb

Overview

Deprecated.

While all possible effort has been made to preserve the original behavior of this class, future improvements to the Driver, Transport, and Verifier subsystems may not be picked up in these Drivers. When legacy Driver::SSHBase support is removed, this class will no longer be available.

Legacy base class for a driver that uses SSH to communication with an instance. This class has been updated to use the Instance’s Transport to issue commands and transfer files and no longer uses the ‘Kitchen:SSH` class directly.

NOTE: Authors of new Drivers are encouraged to inherit from ‘Kitchen::Driver::Base` instead and existing Driver authors are encouraged to update their Driver class to inherit from `Kitchen::Driver::SSHBase`.

A subclass must implement the following methods:

  • #create(state)

  • #destroy(state)

Author:

Direct Known Subclasses

Proxy

Class Attribute Summary collapse

Attributes included from Configurable

#instance

Class Method Summary collapse

Instance Method Summary collapse

Methods included from Logging

#banner, #debug, #error, #fatal, #info, #warn

Methods included from Configurable

#[], #bourne_shell?, #calculate_path, #config_keys, #diagnose, #diagnose_plugin, #finalize_config!, included, #name, #powershell_shell?, #remote_path_join, #unix_os?, #windows_os?

Constructor Details

#initialize(config = {}) ⇒ SSHBase

Creates a new Driver object using the provided configuration data which will be merged with any default configuration.

Parameters:

  • config (Hash) (defaults to: {})

    provided driver configuration



59
60
61
# File 'lib/kitchen/driver/ssh_base.rb', line 59

def initialize(config = {})
  init_config(config)
end

Class Attribute Details

.serial_actionsArray<Symbol> (readonly)

Returns an array of action method names that cannot be run concurrently and must be run in serial via a shared mutex.

Returns:

  • (Array<Symbol>)

    an array of action method names that cannot be run concurrently and must be run in serial via a shared mutex



185
186
187
# File 'lib/kitchen/driver/ssh_base.rb', line 185

def serial_actions
  @serial_actions
end

Class Method Details

.no_parallel_for(*methods) ⇒ Object

Registers certain driver actions that cannot be safely run concurrently in threads across multiple instances. Typically this might be used for create or destroy actions that use an underlying resource that cannot be used at the same time.

A shared mutex for this driver object will be used to synchronize all registered methods.

Examples:

a single action method that cannot be run concurrently


no_parallel_for :create

multiple action methods that cannot be run concurrently


no_parallel_for :create, :destroy

Parameters:

  • methods (Array<Symbol>)

    one or more actions as symbols

Raises:

  • (ClientError)

    if any method is not a valid action method name



206
207
208
209
210
211
212
213
214
215
216
217
# File 'lib/kitchen/driver/ssh_base.rb', line 206

def self.no_parallel_for(*methods)
  action_methods = %i{create converge setup verify destroy}

  Array(methods).each do |meth|
    next if action_methods.include?(meth)

    raise ClientError, "##{meth} is not a valid no_parallel_for method"
  end

  @serial_actions ||= []
  @serial_actions += methods
end

Instance Method Details

#cache_directoryObject

Cache directory that a driver could implement to inform the provisioner that it can leverage it internally



223
# File 'lib/kitchen/driver/ssh_base.rb', line 223

def cache_directory; end

#converge(state) ⇒ Object



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
# File 'lib/kitchen/driver/ssh_base.rb', line 69

def converge(state) # rubocop:disable Metrics/AbcSize
  provisioner = instance.provisioner
  provisioner.create_sandbox
  sandbox_dirs = Util.list_directory(provisioner.sandbox_path)

  instance.transport.connection(backcompat_merged_state(state)) do |conn|
    conn.execute(env_cmd(provisioner.install_command))
    conn.execute(env_cmd(provisioner.init_command))
    info("Transferring files to #{instance.to_str}")
    conn.upload(sandbox_dirs, provisioner[:root_path])
    debug("Transfer complete")
    conn.execute(env_cmd(provisioner.prepare_command))
    conn.execute(env_cmd(provisioner.run_command))
    info("Downloading files from #{instance.to_str}")
    provisioner[:downloads].to_h.each do |remotes, local|
      debug("Downloading #{Array(remotes).join(", ")} to #{local}")
      conn.download(remotes, local)
    end
    debug("Download complete")
  end
rescue Kitchen::Transport::TransportFailed => ex
  raise ActionFailed, ex.message
ensure
  instance.provisioner.cleanup_sandbox
end

#create(state) ⇒ Object

Creates an instance.

Parameters:

  • state (Hash)

    mutable instance and driver state

Raises:



64
65
66
# File 'lib/kitchen/driver/ssh_base.rb', line 64

def create(state) # rubocop:disable Lint/UnusedMethodArgument
  raise ClientError, "#{self.class}#create must be implemented"
end

#destroy(state) ⇒ Object

Destroys an instance.

Parameters:

  • state (Hash)

    mutable instance and driver state

Raises:



127
128
129
# File 'lib/kitchen/driver/ssh_base.rb', line 127

def destroy(state) # rubocop:disable Lint/UnusedMethodArgument
  raise ClientError, "#{self.class}#destroy must be implemented"
end

#legacy_state(state) ⇒ Object



131
132
133
# File 'lib/kitchen/driver/ssh_base.rb', line 131

def legacy_state(state)
  backcompat_merged_state(state)
end

#login_command(state) ⇒ Object



141
142
143
144
# File 'lib/kitchen/driver/ssh_base.rb', line 141

def (state)
  instance.transport.connection(backcompat_merged_state(state))
    .
end

#package(state) ⇒ Object

Package an instance.

(see Base#package)



138
# File 'lib/kitchen/driver/ssh_base.rb', line 138

def package(state); end

#remote_command(state, command) ⇒ Object

Executes an arbitrary command on an instance over an SSH connection.

Parameters:

  • state (Hash)

    mutable instance and driver state

  • command (String)

    the command to be executed

Raises:

  • (ActionFailed)

    if the command could not be successfully completed



151
152
153
154
155
# File 'lib/kitchen/driver/ssh_base.rb', line 151

def remote_command(state, command)
  instance.transport.connection(backcompat_merged_state(state)) do |conn|
    conn.execute(env_cmd(command))
  end
end

#setup(state) ⇒ Object



96
97
98
99
100
101
102
103
104
# File 'lib/kitchen/driver/ssh_base.rb', line 96

def setup(state)
  verifier = instance.verifier

  instance.transport.connection(backcompat_merged_state(state)) do |conn|
    conn.execute(env_cmd(verifier.install_command))
  end
rescue Kitchen::Transport::TransportFailed => ex
  raise ActionFailed, ex.message
end

#ssh(ssh_args, command) ⇒ Object

Deprecated.

This method should no longer be called directly and exists to support very old drivers. This will be removed in the future.

**(Deprecated)** Executes a remote command over SSH.

Parameters:

  • ssh_args (Array)

    ssh arguments

  • command (String)

    remote command to invoke



163
164
165
166
167
168
169
170
171
# File 'lib/kitchen/driver/ssh_base.rb', line 163

def ssh(ssh_args, command)
  pseudo_state = { hostname: ssh_args[0], username: ssh_args[1] }
  pseudo_state.merge!(ssh_args[2])
  connection_state = backcompat_merged_state(pseudo_state)

  instance.transport.connection(connection_state) do |conn|
    conn.execute(env_cmd(command))
  end
end

#verify(state) ⇒ Object



107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
# File 'lib/kitchen/driver/ssh_base.rb', line 107

def verify(state) # rubocop:disable Metrics/AbcSize
  verifier = instance.verifier
  verifier.create_sandbox
  sandbox_dirs = Util.list_directory(verifier.sandbox_path)

  instance.transport.connection(backcompat_merged_state(state)) do |conn|
    conn.execute(env_cmd(verifier.init_command))
    info("Transferring files to #{instance.to_str}")
    conn.upload(sandbox_dirs, verifier[:root_path])
    debug("Transfer complete")
    conn.execute(env_cmd(verifier.prepare_command))
    conn.execute(env_cmd(verifier.run_command))
  end
rescue Kitchen::Transport::TransportFailed => ex
  raise ActionFailed, ex.message
ensure
  instance.verifier.cleanup_sandbox
end

#verify_dependenciesObject

Performs whatever tests that may be required to ensure that this driver will be able to function in the current environment. This may involve checking for the presence of certain directories, software installed, etc.

Raises:

  • (UserError)

    if the driver will not be able to perform or if a documented dependency is missing from the system



180
# File 'lib/kitchen/driver/ssh_base.rb', line 180

def verify_dependencies; end