foreman_snapshot_management 1.6.1 → 2.0.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (62) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +8 -2
  3. data/Rakefile +7 -2
  4. data/app/controllers/api/v2/snapshots_controller.rb +37 -7
  5. data/app/controllers/concerns/foreman/controller/parameters/snapshot.rb +1 -1
  6. data/app/controllers/foreman_snapshot_management/snapshots_controller.rb +5 -5
  7. data/app/models/concerns/fog_extensions/proxmox/snapshots/mock.rb +24 -0
  8. data/app/models/foreman_snapshot_management/proxmox_extensions.rb +101 -0
  9. data/app/models/foreman_snapshot_management/snapshot.rb +28 -28
  10. data/app/models/foreman_snapshot_management/vmware_extensions.rb +40 -13
  11. data/app/views/api/v2/snapshots/base.json.rabl +2 -0
  12. data/app/views/api/v2/snapshots/main.json.rabl +2 -2
  13. data/app/views/foreman_snapshot_management/snapshots/_index.html.erb +12 -74
  14. data/app/views/hosts/_snapshots_tab.html.erb +8 -0
  15. data/lib/foreman_snapshot_management/engine.rb +35 -16
  16. data/lib/foreman_snapshot_management/version.rb +1 -1
  17. data/lib/tasks/foreman_snapshot_management_tasks.rake +2 -2
  18. data/locale/de/LC_MESSAGES/foreman_snapshot_management.mo +0 -0
  19. data/locale/de/foreman_snapshot_management.po +195 -0
  20. data/locale/en/LC_MESSAGES/foreman_snapshot_management.mo +0 -0
  21. data/locale/en/foreman_snapshot_management.po +179 -11
  22. data/locale/foreman_snapshot_management.pot +259 -8
  23. data/locale/gemspec.rb +1 -1
  24. data/package.json +46 -0
  25. data/test/controllers/api/v2/snapshots_test.rb +250 -39
  26. data/test/controllers/foreman_snapshot_management/snapshots_controller_test.rb +61 -9
  27. data/test/factories/proxmox_factory.rb +18 -0
  28. data/test/test_plugin_helper.rb +3 -0
  29. data/webpack/components/SnapshotManagement/SnapshotManagement.js +84 -0
  30. data/webpack/components/SnapshotManagement/SnapshotManagementActions.js +212 -0
  31. data/webpack/components/SnapshotManagement/SnapshotManagementConstants.js +9 -0
  32. data/webpack/components/SnapshotManagement/SnapshotManagementReducer.js +100 -0
  33. data/webpack/components/SnapshotManagement/SnapshotManagementSelectors.js +8 -0
  34. data/webpack/components/SnapshotManagement/__tests__/SnapshotManagementActions.test.js +123 -0
  35. data/webpack/components/SnapshotManagement/__tests__/SnapshotManagementReducer.test.js +157 -0
  36. data/webpack/components/SnapshotManagement/__tests__/__snapshots__/SnapshotManagementActions.test.js.snap +314 -0
  37. data/webpack/components/SnapshotManagement/__tests__/__snapshots__/SnapshotManagementReducer.test.js.snap +214 -0
  38. data/webpack/components/SnapshotManagement/components/SnapshotForm/SnapshotForm.js +118 -0
  39. data/webpack/components/SnapshotManagement/components/SnapshotForm/SnapshotFormConstants.js +5 -0
  40. data/webpack/components/SnapshotManagement/components/SnapshotForm/__tests__/SnapshotForm.test.js +26 -0
  41. data/webpack/components/SnapshotManagement/components/SnapshotForm/__tests__/__snapshots__/SnapshotForm.test.js.snap +476 -0
  42. data/webpack/components/SnapshotManagement/components/SnapshotForm/index.js +19 -0
  43. data/webpack/components/SnapshotManagement/components/SnapshotForm/snapshotForm.scss +3 -0
  44. data/webpack/components/SnapshotManagement/components/SnapshotFormModal/SnapshotFormModal.js +37 -0
  45. data/webpack/components/SnapshotManagement/components/SnapshotFormModal/SnapshotFormModalConstants.js +1 -0
  46. data/webpack/components/SnapshotManagement/components/SnapshotFormModal/__tests__/SnapshotFormModal.test.js +19 -0
  47. data/webpack/components/SnapshotManagement/components/SnapshotFormModal/__tests__/__snapshots__/SnapshotFormModal.test.js.snap +19 -0
  48. data/webpack/components/SnapshotManagement/components/SnapshotFormModal/index.js +12 -0
  49. data/webpack/components/SnapshotManagement/components/SnapshotFormModal/useSnapshotFormModal.js +7 -0
  50. data/webpack/components/SnapshotManagement/components/SnapshotList/SnapshotList.js +314 -0
  51. data/webpack/components/SnapshotManagement/components/SnapshotList/SnapshotListHelper.js +70 -0
  52. data/webpack/components/SnapshotManagement/components/SnapshotList/__tests__/SnapshotList.test.js +88 -0
  53. data/webpack/components/SnapshotManagement/components/SnapshotList/__tests__/__snapshots__/SnapshotList.test.js.snap +1081 -0
  54. data/webpack/components/SnapshotManagement/components/SnapshotList/snapshotList.scss +13 -0
  55. data/webpack/components/SnapshotManagement/index.js +33 -0
  56. data/webpack/components/SnapshotManagement/snapshotManagement.scss +5 -0
  57. data/webpack/global_index.js +7 -0
  58. data/webpack/global_test_setup.js +11 -0
  59. data/webpack/index.js +8 -0
  60. data/webpack/reducers.js +7 -0
  61. data/webpack/test_setup.js +17 -0
  62. metadata +50 -37
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: f1f7ac4fa53eca310f5b7effafa4fca21cfdf0ce1f97981892165dfa9ebc1f19
4
- data.tar.gz: 1440f1529c9d5c02428dac9371f1d02faca2ea6c95064e51c4efa900bed5126a
3
+ metadata.gz: 852f360b2e273ab1e59ba5b2e7960633cdfc169acd60e98f8fc9abeb2616a098
4
+ data.tar.gz: 9c292f218d3f01ef7e3cba1eab5caaac82e94a65891d88a1b11f19952da39c8a
5
5
  SHA512:
6
- metadata.gz: 41df800a5a9d08c2dac58f5bc1319840dbdaa39ee1e4cf79ef71677645cc9d64cee3de0cf310d49e0d16ba9fc41a820ae42bf31f848398d040610b42ecd88649
7
- data.tar.gz: ca5116f54a696fbe6062d05369747a02898a283276252ae118884b075ac01fe05a3864cbf583f2cfcf6b57801283e278ac4c0949f9bf0c5ae918262cf6a7468f
6
+ metadata.gz: ca9602895984df366f86addc657df08ce8c2c2e69fedd9d554115829f36bd956838fb05d2eb3a7d5a6c9a4d0af9f5385ac40573804bb54e9766be6014a49acf9
7
+ data.tar.gz: 949d446c4f72c2ad58c4098d5866d53259151bb35597444f402b3fd08a3d68ba5f4e76a975bab5be16098b13e4ebbb16531b841869cbd6e53ca31ff99cd924ae
data/README.md CHANGED
@@ -1,9 +1,12 @@
1
- [![Build Status](https://travis-ci.org/ATIX-AG/foreman_snapshot_management.svg?branch=master)](https://travis-ci.org/ATIX-AG/foreman_snapshot_management)
1
+ [![React Testing](https://github.com/ATIX-AG/foreman_snapshot_management/actions/workflows/react.yml/badge.svg)](https://github.com/ATIX-AG/foreman_snapshot_management/actions/workflows/react.yml)
2
+ [![Ruby Testing](https://github.com/ATIX-AG/foreman_snapshot_management/actions/workflows/ruby.yml/badge.svg)](https://github.com/ATIX-AG/foreman_snapshot_management/actions/workflows/ruby.yml)
2
3
 
3
4
  # ForemanSnapshotManagement
4
5
 
5
6
  ForemanSnapshotManagement is a Foreman plugin to manage snapshots.
6
- As Hypervisor VMware vSphere is supported.
7
+ As Hypervisor the following systems are supported:
8
+ - VMware vSphere
9
+ - [Proxmox](https://www.proxmox.com/)
7
10
 
8
11
  ## Features
9
12
 
@@ -20,6 +23,9 @@ See [How_to_Install_a_Plugin](http://projects.theforeman.org/projects/foreman/wi
20
23
 
21
24
  | Foreman Version | Plugin Version |
22
25
  | --------------- | -------------- |
26
+ | 2.3 | >= 2.0.0 |
27
+ | 1.24 | >= 1.7.0 |
28
+ | 1.23 | >= 1.7.0 |
23
29
  | 1.22 | >= 1.6.0 |
24
30
  | 1.21 | >= 1.5.0 |
25
31
  | 1.20 | >= 1.5.0 |
data/Rakefile CHANGED
@@ -14,6 +14,13 @@ rescue LoadError
14
14
  RDoc::Task = Rake::RDocTask
15
15
  end
16
16
 
17
+ begin
18
+ require 'rubocop/rake_task'
19
+ RuboCop::RakeTask.new
20
+ rescue StandardError => _e
21
+ puts 'Rubocop not loaded.'
22
+ end
23
+
17
24
  RDoc::Task.new(:rdoc) do |rdoc|
18
25
  rdoc.rdoc_dir = 'rdoc'
19
26
  rdoc.title = 'ForemanSnapshotManagement'
@@ -22,6 +29,4 @@ RDoc::Task.new(:rdoc) do |rdoc|
22
29
  rdoc.rdoc_files.include('lib/**/*.rb')
23
30
  end
24
31
 
25
- APP_RAKEFILE = File.expand_path('test/dummy/Rakefile', __dir__)
26
-
27
32
  Bundler::GemHelper.install_tasks
@@ -6,14 +6,28 @@ module Api
6
6
  include Api::Version2
7
7
  include Foreman::Controller::Parameters::Snapshot
8
8
 
9
- before_action :find_required_nested_object
9
+ before_action :find_host
10
10
  before_action :check_snapshot_capability
11
11
  before_action :find_resource, :only => %w[show update destroy revert]
12
12
 
13
13
  api :GET, '/hosts/:host_id/snapshots', N_('List all snapshots')
14
14
  param :host_id, :identifier_dottable, :required => true
15
+ param_group :search_and_pagination, ::Api::V2::BaseController
16
+ meta :search => [{ :name => 'name', :type => 'string' }]
15
17
  def index
16
- @snapshots = resource_scope_for_index
18
+ if params[:search]
19
+ search = params[:search].match(/^\s*name\s*=\s*(\w+)\s*$/) || params[:search].match(/^\s*name\s*=\s*\"([^"]+)\"\s*$/)
20
+ raise "Field '#{params[:search]}' not recognized for searching!" unless search
21
+
22
+ snapshot = resource_class.find_for_host_by_name(@host, search[1])
23
+ @snapshots = if snapshot
24
+ [snapshot].paginate(paginate_options)
25
+ else
26
+ []
27
+ end
28
+ else
29
+ @snapshots = resource_scope_for_index
30
+ end
17
31
  end
18
32
 
19
33
  api :GET, '/hosts/:host_id/snapshots/:id', 'Show a snapshot'
@@ -35,7 +49,7 @@ module Api
35
49
  param_group :snapshot, :as => :create
36
50
 
37
51
  def create
38
- @snapshot = resource_class.new(snapshot_params.to_h.merge(host: @nested_obj).merge(include_ram: params[:include_ram]))
52
+ @snapshot = resource_class.new(snapshot_params.to_h.merge(host: @host).merge(include_ram: params[:include_ram]))
39
53
  process_response @snapshot.create
40
54
  end
41
55
 
@@ -45,7 +59,7 @@ module Api
45
59
  param_group :snapshot
46
60
 
47
61
  def update
48
- process_response @snapshot.update_attributes(snapshot_params)
62
+ process_response @snapshot.update(snapshot_params)
49
63
  end
50
64
 
51
65
  api :DELETE, '/hosts/:host_id/snapshots/:id', N_('Delete a snapshot')
@@ -66,9 +80,25 @@ module Api
66
80
 
67
81
  private
68
82
 
83
+ # Find Host
84
+ #
85
+ # This method is responsible that methods of the controller know the current host.
86
+ def find_host
87
+ host_id = params[:host_id]
88
+ if host_id.blank?
89
+ not_found
90
+ return false
91
+ end
92
+ @host = Host.authorized("#{action_permission}_snapshots".to_sym, Host).friendly.find(host_id)
93
+ return @host if @host
94
+
95
+ not_found
96
+ false
97
+ end
98
+
69
99
  def resource_scope(_options = {})
70
100
  # TODO: Ask host for snapshots
71
- @resource_scope ||= resource_class.all_for_host(@nested_obj)
101
+ @resource_scope ||= resource_class.all_for_host(@host)
72
102
  end
73
103
 
74
104
  def resource_scope_for_index
@@ -80,12 +110,12 @@ module Api
80
110
  end
81
111
 
82
112
  def find_resource
83
- @snapshot = resource_class.find_for_host(@nested_obj, params[:id])
113
+ @snapshot = resource_class.find_for_host(@host, params[:id])
84
114
  not_found unless @snapshot
85
115
  end
86
116
 
87
117
  def check_snapshot_capability
88
- not_found unless @nested_obj.compute_resource&.capabilities&.include?(:snapshots)
118
+ not_found unless @host.compute_resource&.capabilities&.include?(:snapshots)
89
119
  end
90
120
 
91
121
  def action_permission
@@ -6,7 +6,7 @@ module Foreman::Controller::Parameters::Snapshot
6
6
  class_methods do
7
7
  def snapshot_params_filter
8
8
  Foreman::ParameterFilter.new(::ForemanSnapshotManagement::Snapshot).tap do |filter|
9
- filter.permit :name, :description
9
+ filter.permit :name, :description, :include_ram, :host_id
10
10
  end
11
11
  end
12
12
  end
@@ -66,7 +66,7 @@ module ForemanSnapshotManagement
66
66
  #
67
67
  # This method renames a Snapshot from a given host.
68
68
  def update
69
- if @snapshot.update_attributes(snapshot_params)
69
+ if @snapshot.update(snapshot_params)
70
70
  render json: { name: @snapshot.name, description: @snapshot.description }
71
71
  else
72
72
  msg = _('Failed to update Snapshot: %s') % @snapshot.errors.full_messages.to_sentence
@@ -89,7 +89,7 @@ module ForemanSnapshotManagement
89
89
  errors << [h.name, s.errors.full_messages.to_sentence]
90
90
  end
91
91
  end
92
- error _('Error occurred while creating Snapshot for<br /><dl>%s</dl>') % errors.map { |e| "<dt>#{e[0]}</dt><dd>#{e[1]}</dd>" }.join('<br />') unless errors.empty?
92
+ error _('Error occurred while creating Snapshot for:%s') % "<br /><dl>#{errors.map { |e| "<dt>#{e[0]}</dt><dd>#{e[1]}</dd>" }.join('<br />')}</dl>" unless errors.empty?
93
93
  if snapshots_created.positive?
94
94
  msg = _('Created %{snapshots} for %{num} %{hosts}') % {
95
95
  snapshots: n_('Snapshot', 'Snapshots', snapshots_created),
@@ -143,10 +143,10 @@ module ForemanSnapshotManagement
143
143
  end
144
144
 
145
145
  @hosts
146
- rescue StandardError => error
147
- message = _('Something went wrong while selecting hosts - %s') % error
146
+ rescue StandardError => e
147
+ message = _('Something went wrong while selecting hosts - %s') % e
148
148
  error(message)
149
- Foreman::Logging.exception(message, error)
149
+ Foreman::Logging.exception(message, e)
150
150
  redirect_to hosts_path
151
151
  false
152
152
  end
@@ -0,0 +1,24 @@
1
+ # frozen_string_literal: true
2
+
3
+ module FogExtensions
4
+ module Proxmox
5
+ module Snapshots
6
+ module Mock
7
+ def status_task(_node, _upid)
8
+ {
9
+ 'type' => 'qmsnapshot',
10
+ 'starttime' => 1_580_720_848,
11
+ 'pstart' => 1_864_464_143,
12
+ 'node' => 'proxmox',
13
+ 'upid' => 'UPID:proxmox:00003E13:6F21770F:5E37E2D0:qmsnapshot:100:root@pam:',
14
+ 'user' => 'root@pam',
15
+ 'exitstatus' => 'OK',
16
+ 'status' => 'stopped',
17
+ 'id' => '100',
18
+ 'pid' => 15_891
19
+ }
20
+ end
21
+ end
22
+ end
23
+ end
24
+ end
@@ -0,0 +1,101 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ForemanSnapshotManagement
4
+ module ProxmoxExtensions
5
+ # Extend Proxmox's capabilities with snapshots.
6
+ def capabilities
7
+ super + [:snapshots]
8
+ end
9
+
10
+ # Create a Snapshot.
11
+ #
12
+ # This method creates a Snapshot with a given name and optional description.
13
+ def create_snapshot(host, name, description, _include_ram = false)
14
+ server = find_vm_by_uuid host.uuid
15
+ raise _('Name must contain at least 2 characters starting with alphabet. Valid characters are A-Z a-z 0-9 _') unless /^[A-Za-z][\w]{1,}$/.match?(name)
16
+
17
+ snapshot = server.snapshots.create(name: name)
18
+ snapshot.description = description
19
+ snapshot.update
20
+ rescue StandardError => e
21
+ Foreman::Logging.exception('Error creating Proxmox Snapshot', e)
22
+ raise ::Foreman::WrappedException.new(e, N_('Unable to create Proxmox Snapshot'))
23
+ end
24
+
25
+ # Remove Snapshot
26
+ #
27
+ # This method removes a Snapshot from a given host.
28
+ def remove_snapshot(snapshot)
29
+ snapshot.destroy
30
+ rescue StandardError => e
31
+ Foreman::Logging.exception('Error removing Proxmox Snapshot', e)
32
+ raise ::Foreman::WrappedException.new(e, N_('Unable to remove Proxmox Snapshot'))
33
+ end
34
+
35
+ # Revert Snapshot
36
+ #
37
+ # This method revert a host to a given Snapshot.
38
+ def revert_snapshot(snapshot)
39
+ snapshot.rollback
40
+ rescue StandardError => e
41
+ Foreman::Logging.exception('Error reverting Proxmox Snapshot', e)
42
+ raise ::Foreman::WrappedException.new(e, N_('Unable to revert Proxmox Snapshot'))
43
+ end
44
+
45
+ # Update Snapshot
46
+ #
47
+ # This method renames a Snapshot from a given host.
48
+ def update_snapshot(snapshot, name, description)
49
+ raise _('Snapshot name cannot be changed') if snapshot.name != name
50
+
51
+ snapshot.description = description
52
+ snapshot.update
53
+ rescue StandardError => e
54
+ Foreman::Logging.exception('Error updating Proxmox Snapshot', e)
55
+ raise ::Foreman::WrappedException.new(e, N_('Unable to update Proxmox Snapshot'))
56
+ end
57
+
58
+ # Get Snapshot
59
+ #
60
+ # This methods returns a specific Snapshot for a given host.
61
+ def get_snapshot(host, snapshot_id)
62
+ server = find_vm_by_uuid host.uuid
63
+ snapshot = server.snapshots.get(snapshot_id)
64
+ raw_to_snapshot(host, snapshot)
65
+ end
66
+
67
+ # Get Snapshot by name
68
+ #
69
+ # This method returns a specific Snapshot for a given host.
70
+ def get_snapshot_by_name(host, name)
71
+ server = find_vm_by_uuid host.uuid
72
+ snapshot = server.snapshots.get(name)
73
+ raw_to_snapshot(host, snapshot) if snapshot
74
+ end
75
+
76
+ # Get Snapshots
77
+ #
78
+ # This methods returns Snapshots for a given host.
79
+ def get_snapshots(host)
80
+ server = find_vm_by_uuid host.uuid
81
+ server.snapshots.delete(server.snapshots.get('current'))
82
+ server.snapshots.map do |snapshot|
83
+ raw_to_snapshot(host, snapshot)
84
+ end
85
+ end
86
+
87
+ private
88
+
89
+ def raw_to_snapshot(host, raw_snapshot)
90
+ if raw_snapshot
91
+ Snapshot.new(
92
+ host: host,
93
+ id: raw_snapshot.name,
94
+ raw_snapshot: raw_snapshot,
95
+ name: raw_snapshot.name,
96
+ description: raw_snapshot.description
97
+ )
98
+ end
99
+ end
100
+ end
101
+ end
@@ -5,6 +5,7 @@ require 'date'
5
5
  module ForemanSnapshotManagement
6
6
  class Snapshot
7
7
  extend ActiveModel::Callbacks
8
+ extend ActiveModel::Naming
8
9
  include ActiveModel::Conversion
9
10
  include ActiveModel::Model
10
11
  include ActiveModel::Dirty
@@ -16,40 +17,39 @@ module ForemanSnapshotManagement
16
17
  attr_reader :name, :description, :include_ram, :host_id
17
18
  define_attribute_methods :name, :description, :include_ram
18
19
 
19
- def self.all_for_host(host)
20
- host.compute_resource.get_snapshots(host.uuid).map do |raw_snapshot|
21
- new_from_vmware(host, raw_snapshot)
22
- end
20
+ def self.model_name
21
+ Struct.new(:name, :klass, :singular, :plural, :element,
22
+ :human, :collection, :param_key, :i18n_key, :route_key, :singular_route_key).new(
23
+ 'ForemanSnapshotManagement::Snapshot', ForemanSnapshotManagement::Snapshot,
24
+ 'foreman_snapshot_management_snapshot', 'foreman_snapshot_management_snapshots',
25
+ 'snapshot', 'Snapshot', 'foreman_snapshot_management/snapshots',
26
+ 'snapshot', :'foreman_snapshot_management/snapshot', 'foreman_snapshot_management_snapshots',
27
+ 'foreman_snapshot_management_snapshot'
28
+ )
23
29
  end
24
30
 
25
- def self.find_for_host(host, id)
26
- raw_snapshot = host.compute_resource.get_snapshot(host.uuid, id)
27
- new_from_vmware(host, raw_snapshot) if raw_snapshot
31
+ def self.any?
32
+ true
33
+ end
34
+
35
+ def self.new_for_host(host)
36
+ host.compute_resource.new_snapshot(host)
28
37
  end
29
38
 
30
- def self.new_from_vmware(host, raw_snapshot, opts = {})
31
- new(
32
- host: host,
33
- id: raw_snapshot.ref,
34
- raw_snapshot: raw_snapshot,
35
- name: raw_snapshot.name,
36
- description: raw_snapshot.description,
37
- parent: opts[:parent],
38
- create_time: raw_snapshot.create_time
39
- )
39
+ def self.all_for_host(host)
40
+ host.compute_resource.get_snapshots(host)
40
41
  end
41
42
 
42
- def children
43
- return [] unless raw_snapshot
43
+ def self.find_for_host(host, id)
44
+ host.compute_resource.get_snapshot(host, id)
45
+ end
44
46
 
45
- child_snapshots = raw_snapshot.child_snapshots.flat_map do |child_snapshot|
46
- self.class.new_from_vmware(host, child_snapshot, parent: self)
47
- end
48
- child_snapshots + child_snapshots.flat_map(&:children)
47
+ def self.find_for_host_by_name(host, name)
48
+ host.compute_resource.get_snapshot_by_name(host, name)
49
49
  end
50
50
 
51
51
  def inspect
52
- "#<#{self.class}:0x#{self.__id__.to_s(16)} name=#{name} id=#{id} description=#{description} host_id=#{host_id} parent=#{parent.try(:id)} children=#{children.map(&:id).inspect}>"
52
+ "#<#{self.class}:0x#{self.__id__.to_s(16)} name=#{name} id=#{id} description=#{description} host_id=#{host_id} parent=#{parent.try(:id)}>"
53
53
  end
54
54
 
55
55
  def to_s
@@ -57,7 +57,7 @@ module ForemanSnapshotManagement
57
57
  end
58
58
 
59
59
  def formatted_create_time
60
- create_time.strftime('%F %H:%M')
60
+ create_time&.strftime('%F %H:%M')
61
61
  end
62
62
 
63
63
  def persisted?
@@ -111,7 +111,7 @@ module ForemanSnapshotManagement
111
111
  end
112
112
  end
113
113
 
114
- def update_attributes(new_attributes)
114
+ def update(new_attributes)
115
115
  assign_attributes(new_attributes)
116
116
  save if changed?
117
117
  end
@@ -122,7 +122,7 @@ module ForemanSnapshotManagement
122
122
  handle_snapshot_errors do
123
123
  host.audit_comment = "Create snapshot #{name}"
124
124
  host.save!
125
- host.compute_resource.create_snapshot(host.uuid, name, description, include_ram)
125
+ host.compute_resource.create_snapshot(host, name, description, include_ram)
126
126
  changes_applied
127
127
  end
128
128
  end
@@ -144,7 +144,7 @@ module ForemanSnapshotManagement
144
144
  result = handle_snapshot_errors do
145
145
  host.audit_comment = "Destroy snapshot #{name}"
146
146
  host.save!
147
- result = host.compute_resource.remove_snapshot(raw_snapshot, false)
147
+ result = host.compute_resource.remove_snapshot(raw_snapshot)
148
148
  end
149
149
  @id = nil
150
150
  result
@@ -4,14 +4,14 @@ module ForemanSnapshotManagement
4
4
  module VmwareExtensions
5
5
  # Extend VMWare's capabilities with snapshots.
6
6
  def capabilities
7
- super + [:snapshots]
7
+ super + [:snapshots, :snapshot_include_ram, :editable_snapshot_name]
8
8
  end
9
9
 
10
10
  # Create a Snapshot.
11
11
  #
12
12
  # This method creates a Snapshot with a given name and optional description.
13
- def create_snapshot(uuid, name, description, include_ram = false)
14
- task = client.vm_take_snapshot('instance_uuid' => uuid, 'name' => name, 'description' => description, 'memory' => include_ram)
13
+ def create_snapshot(host, name, description, include_ram = false)
14
+ task = client.vm_take_snapshot('instance_uuid' => host.uuid, 'name' => name, 'description' => description, 'memory' => include_ram)
15
15
  task_successful?(task)
16
16
  rescue RbVmomi::Fault => e
17
17
  Foreman::Logging.exception('Error creating VMWare Snapshot', e)
@@ -21,7 +21,7 @@ module ForemanSnapshotManagement
21
21
  # Remove Snapshot
22
22
  #
23
23
  # This method removes a Snapshot from a given host.
24
- def remove_snapshot(snapshot, remove_children)
24
+ def remove_snapshot(snapshot, remove_children = false)
25
25
  task = client.remove_snapshot('snapshot' => snapshot, 'removeChildren' => remove_children)
26
26
  task_successful?(task)
27
27
  rescue RbVmomi::Fault => e
@@ -54,23 +54,50 @@ module ForemanSnapshotManagement
54
54
  # Get Snapshot
55
55
  #
56
56
  # This methods returns a specific Snapshot for a given host.
57
- def get_snapshot(server_id, snapshot_id)
58
- snapshot = client.snapshots(server_id: server_id).get(snapshot_id)
59
- # Workaround for https://github.com/fog/fog-vsphere/commit/d808255cd19c3d43d3227825f1e0d72d3f6ee6b9
60
- # Remove, when fog-vshpere 1.11 lands in foreman
61
- snapshot = snapshot.get_child(snapshot_id) while snapshot && snapshot.ref != snapshot_id
62
- snapshot
57
+ def get_snapshot(host, snapshot_id)
58
+ raw_snapshot = client.snapshots(server_id: host.uuid).get(snapshot_id)
59
+ raw_to_snapshot(host, raw_snapshot)
60
+ end
61
+
62
+ # Get Snapshot by name
63
+ #
64
+ # This method returns a specific Snapshot for a given host.
65
+ def get_snapshot_by_name(host, name)
66
+ raw_snapshot = nil
67
+ client.snapshots(server_id: host.uuid).all(recursive: true).each do |snapshot|
68
+ if name == snapshot.name
69
+ raw_snapshot = snapshot
70
+ break
71
+ end
72
+ end
73
+ raw_to_snapshot(host, raw_snapshot)
63
74
  end
64
75
 
65
76
  # Get Snapshots
66
77
  #
67
- # This methods returns Snapshots from a given host.
68
- def get_snapshots(server_id)
69
- client.snapshots(server_id: server_id).all(recursive: true)
78
+ # This methods returns Snapshots for a given host.
79
+ def get_snapshots(host)
80
+ client.snapshots(server_id: host.uuid).all(recursive: true).map do |raw_snapshot|
81
+ raw_to_snapshot(host, raw_snapshot)
82
+ end
70
83
  end
71
84
 
72
85
  private
73
86
 
87
+ def raw_to_snapshot(host, raw_snapshot, opts = {})
88
+ if raw_snapshot
89
+ Snapshot.new(
90
+ host: host,
91
+ id: raw_snapshot.ref,
92
+ raw_snapshot: raw_snapshot,
93
+ name: raw_snapshot.name,
94
+ description: raw_snapshot.description,
95
+ parent: opts[:parent],
96
+ create_time: raw_snapshot.create_time
97
+ )
98
+ end
99
+ end
100
+
74
101
  def task_successful?(task)
75
102
  task['task_state'] == 'success' || task['state'] == 'success'
76
103
  end