Class: Bosh::Clouds::Dummy

Inherits:
Object show all
Defined in:
lib/cloud/dummy.rb

Defined Under Namespace

Classes: CommandTransport, ConfigureNetworksCommand, CreateVmCommand, NotImplemented

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(options) ⇒ Dummy

Returns a new instance of Dummy.



12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
# File 'lib/cloud/dummy.rb', line 12

def initialize(options)
  @options = options

  @base_dir = options['dir']
  if @base_dir.nil?
    raise ArgumentError, 'Must specify dir'
  end

  @running_vms_dir = File.join(@base_dir, 'running_vms')
  @tmp_dir = File.join(@base_dir, 'tmp')
  FileUtils.mkdir_p(@tmp_dir)

  @logger = Logging::Logger.new('DummyCPI')
  @logger.add_appenders(Logging.appenders.io(
    'DummyCPIIO',
    options['log_buffer'] || STDOUT
  ))

  @commands = CommandTransport.new(@base_dir, @logger)

  FileUtils.mkdir_p(@base_dir)
rescue Errno::EACCES
  raise ArgumentError, "cannot create dummy cloud base directory #{@base_dir}"
end

Instance Attribute Details

#commandsObject (readonly)

Returns the value of attribute commands.



10
11
12
# File 'lib/cloud/dummy.rb', line 10

def commands
  @commands
end

Instance Method Details

#agent_log_path(agent_id) ⇒ Object



188
189
190
# File 'lib/cloud/dummy.rb', line 188

def agent_log_path(agent_id)
  "#{@base_dir}/agent.#{agent_id}.log"
end

#attach_disk(vm_id, disk_id) ⇒ Object



121
122
123
124
125
126
127
128
129
130
# File 'lib/cloud/dummy.rb', line 121

def attach_disk(vm_id, disk_id)
  file = attachment_file(vm_id, disk_id)
  FileUtils.mkdir_p(File.dirname(file))
  FileUtils.touch(file)

  agent_id = agent_id_for_vm_id(vm_id)
  settings = read_agent_settings(agent_id)
  settings['disks']['persistent'][disk_id] = 'attached'
  write_agent_settings(agent_id, settings)
end

#configure_networks(vm_id, networks) ⇒ Object



110
111
112
113
114
115
116
117
118
119
# File 'lib/cloud/dummy.rb', line 110

def configure_networks(vm_id, networks)
  cmd = commands.next_configure_networks_cmd(vm_id)

  # The only configure_networks test so far only tests the negative case.
  # If a positive case is added, the agent will need to be re-started.
  # Normally runit would handle that.
  if cmd.not_supported || true
    raise NotSupported, 'Dummy CPI was configured to return NotSupported'
  end
end

#create_disk(size, cloud_properties, vm_locality = nil) ⇒ Object



141
142
143
144
145
146
147
# File 'lib/cloud/dummy.rb', line 141

def create_disk(size, cloud_properties, vm_locality = nil)
  disk_id = SecureRandom.hex
  file = disk_file(disk_id)
  FileUtils.mkdir_p(File.dirname(file))
  File.write(file, size.to_s)
  disk_id
end

#create_stemcell(image, _) ⇒ Object



37
38
39
40
41
# File 'lib/cloud/dummy.rb', line 37

def create_stemcell(image, _)
  stemcell_id = Digest::SHA1.hexdigest(File.read(image))
  File.write(stemcell_file(stemcell_id), image)
  stemcell_id
end

#create_vm(agent_id, stemcell, resource_pool, networks, disk_locality = nil, env = nil) ⇒ Object

rubocop:disable ParameterLists



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
# File 'lib/cloud/dummy.rb', line 48

def create_vm(agent_id, stemcell, resource_pool, networks, disk_locality = nil, env = nil)
# rubocop:enable ParameterLists
  @logger.info('Dummy: create_vm')

  ips = []
  cmd = commands.next_create_vm_cmd

  if cmd.ip_address
    # special case used by dynamic IP assignment tests: CPI always chooses its own IP
    write_agent_default_network(agent_id, cmd.ip_address)
    ips << { 'network' => 'cloud', 'ip' => cmd.ip_address }
  else
    networks.each do |network_name, network|
      ips << { 'network' => network_name, 'ip' => network['ip'] }
    end
  end

  allocate_ips(ips)

  write_agent_settings(agent_id, {
    agent_id: agent_id,
    blobstore: @options['agent']['blobstore'],
    ntp: [],
    disks: { persistent: {} },
    networks: networks,
    vm: { name: "vm-#{agent_id}" },
    cert: '',
    mbus: @options['nats'],
  })

  agent_pid = spawn_agent_process(agent_id)

  FileUtils.mkdir_p(@running_vms_dir)
  File.write(vm_file(agent_pid), JSON.dump("agent_id" => agent_id, "ips" => ips))

  agent_pid.to_s
end

#delete_disk(disk_id) ⇒ Object



149
150
151
# File 'lib/cloud/dummy.rb', line 149

def delete_disk(disk_id)
  FileUtils.rm(disk_file(disk_id))
end

#delete_snapshot(snapshot_id) ⇒ Object



161
162
163
# File 'lib/cloud/dummy.rb', line 161

def delete_snapshot(snapshot_id)
  FileUtils.rm(snapshot_file(snapshot_id))
end

#delete_stemcell(stemcell_cid) ⇒ Object



43
44
45
# File 'lib/cloud/dummy.rb', line 43

def delete_stemcell(stemcell_cid)
  FileUtils.rm(stemcell_file(stemcell_cid))
end

#delete_vm(vm_name) ⇒ Object



86
87
88
89
90
91
92
93
94
95
96
# File 'lib/cloud/dummy.rb', line 86

def delete_vm(vm_name)
  agent_pid = vm_name.to_i
  Process.kill('KILL', agent_pid)
  # rubocop:disable HandleExceptions
rescue Errno::EINVAL, Errno::ESRCH, Errno::EPERM => e
  # rubocop:enable HandleExceptions
  @logger.info("Dummy CPI delete_vm failed for agent pid #{vm_name}. #{e}")
ensure
  free_ips(ips_for_vm_id(vm_name)) if has_vm?(vm_name)
  FileUtils.rm_rf(File.join(@base_dir, 'running_vms', vm_name))
end

#detach_disk(vm_id, disk_id) ⇒ Object



132
133
134
135
136
137
138
139
# File 'lib/cloud/dummy.rb', line 132

def detach_disk(vm_id, disk_id)
  FileUtils.rm(attachment_file(vm_id, disk_id))

  agent_id = agent_id_for_vm_id(vm_id)
  settings = read_agent_settings(agent_id)
  settings['disks']['persistent'].delete(disk_id)
  write_agent_settings(agent_id, settings)
end

#disk_cidsObject



172
173
174
175
# File 'lib/cloud/dummy.rb', line 172

def disk_cids
  # Shuffle so that no one relies on the order of disks
  Dir.glob(disk_file('*')).map { |disk| File.basename(disk) }.shuffle
end

#has_disk?(disk_id) ⇒ Boolean

Returns:

  • (Boolean)


106
107
108
# File 'lib/cloud/dummy.rb', line 106

def has_disk?(disk_id)
  File.exists?(disk_file(disk_id))
end

#has_vm?(vm_id) ⇒ Boolean

Returns:

  • (Boolean)


102
103
104
# File 'lib/cloud/dummy.rb', line 102

def has_vm?(vm_id)
  File.exists?(vm_file(vm_id))
end

#kill_agentsObject



177
178
179
180
181
182
183
184
185
186
# File 'lib/cloud/dummy.rb', line 177

def kill_agents
  vm_cids.each do |agent_pid|
    begin
      Process.kill('KILL', agent_pid.to_i)
    # rubocop:disable HandleExceptions
    rescue Errno::ESRCH
    # rubocop:enable HandleExceptions
    end
  end
end

#reboot_vm(vm_id) ⇒ Object

Raises:



98
99
100
# File 'lib/cloud/dummy.rb', line 98

def reboot_vm(vm_id)
  raise NotImplemented, 'Dummy CPI does not implement reboot_vm'
end

#set_vm_metadata(vm, metadata) ⇒ Object



192
# File 'lib/cloud/dummy.rb', line 192

def (vm, ); end

#snapshot_disk(_, metadata) ⇒ Object



153
154
155
156
157
158
159
# File 'lib/cloud/dummy.rb', line 153

def snapshot_disk(_, )
  snapshot_id = SecureRandom.hex
  file = snapshot_file(snapshot_id)
  FileUtils.mkdir_p(File.dirname(file))
  File.write(file, .to_json)
  snapshot_id
end

#vm_cidsObject

Additional Dummy test helpers



167
168
169
170
# File 'lib/cloud/dummy.rb', line 167

def vm_cids
  # Shuffle so that no one relies on the order of VMs
  Dir.glob(File.join(@running_vms_dir, '*')).map { |vm| File.basename(vm) }.shuffle
end